From 1f5b2726b5e80d1f6535162297571d38333fbf38 Mon Sep 17 00:00:00 2001 From: andrew-wilcox Date: Wed, 15 May 2024 06:36:34 -0600 Subject: [PATCH 01/46] added auto hit and 2x damage from certain moves when targeting a pokemon that used minimize (#824) * added auto hit and 2x damage from certain moves when targetting a pokemon who used minimize * review fixes and bad merge * review fixes and bad merge v2 * changed to be double damage instead of power for the minimize condition * added TSdocs for function] * remove ability to add minimize tag to dynamax-mons * status cannot be applied to max-mons, and falls off if they dynamax * updated doccumentation * Update move.ts --------- Co-authored-by: Cae Rulius Co-authored-by: Benjamin Odom --- src/data/battler-tags.ts | 29 +++++++++++++++++++++ src/data/enums/battler-tag-type.ts | 3 ++- src/data/move.ts | 42 +++++++++++++++++++++++++++++- src/field/pokemon.ts | 6 +++++ 4 files changed, 78 insertions(+), 2 deletions(-) diff --git a/src/data/battler-tags.ts b/src/data/battler-tags.ts index 257f56d46ed..f66b5b2a0d9 100644 --- a/src/data/battler-tags.ts +++ b/src/data/battler-tags.ts @@ -544,6 +544,33 @@ export class AquaRingTag extends BattlerTag { } } +/** Tag used to allow moves that interact with {@link Moves.MINIMIZE} to function */ +export class MinimizeTag extends BattlerTag { + constructor() { + super(BattlerTagType.MINIMIZED, BattlerTagLapseType.TURN_END, 1, Moves.MINIMIZE, undefined); + } + + canAdd(pokemon: Pokemon): boolean { + return !pokemon.isMax(); + } + + onAdd(pokemon: Pokemon): void { + super.onAdd(pokemon); + } + + lapse(pokemon: Pokemon, lapseType: BattlerTagLapseType): boolean { + //If a pokemon dynamaxes they lose minimized status + if(pokemon.isMax()){ + return false + } + return lapseType !== BattlerTagLapseType.CUSTOM || super.lapse(pokemon, lapseType); + } + + onRemove(pokemon: Pokemon): void { + super.onRemove(pokemon); + } +} + export class DrowsyTag extends BattlerTag { constructor() { super(BattlerTagType.DROWSY, BattlerTagLapseType.TURN_END, 2, Moves.YAWN); @@ -1358,6 +1385,8 @@ export function getBattlerTag(tagType: BattlerTagType, turnCount: integer, sourc return new TypeBoostTag(tagType, sourceMove, Type.ELECTRIC, 2, true); case BattlerTagType.MAGNET_RISEN: return new MagnetRisenTag(tagType, sourceMove); + case BattlerTagType.MINIMIZED: + return new MinimizeTag(); case BattlerTagType.NONE: default: return new BattlerTag(tagType, BattlerTagLapseType.CUSTOM, turnCount, sourceMove, sourceId); diff --git a/src/data/enums/battler-tag-type.ts b/src/data/enums/battler-tag-type.ts index d18ccf1c52f..9411d70a670 100644 --- a/src/data/enums/battler-tag-type.ts +++ b/src/data/enums/battler-tag-type.ts @@ -55,5 +55,6 @@ export enum BattlerTagType { CURSED = "CURSED", CHARGED = "CHARGED", GROUNDED = "GROUNDED", - MAGNET_RISEN = "MAGNET_RISEN" + MAGNET_RISEN = "MAGNET_RISEN", + MINIMIZED = "MINIMIZED" } diff --git a/src/data/move.ts b/src/data/move.ts index 5f5765c1d7c..46216eb754a 100644 --- a/src/data/move.ts +++ b/src/data/move.ts @@ -2480,6 +2480,30 @@ export class ThunderAccuracyAttr extends VariableAccuracyAttr { } } +/** + * Attribute used for moves which never miss + * against Pokemon with the {@link BattlerTagType.MINIMIZED} + * @see {@link apply} + * @param user N/A + * @param target Target of the move + * @param move N/A + * @param args [0] Accuracy of the move to be modified + * @returns true if the function succeeds + */ +export class MinimizeAccuracyAttr extends VariableAccuracyAttr{ + + apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { + if (target.getTag(BattlerTagType.MINIMIZED)){ + const accuracy = args[0] as Utils.NumberHolder + accuracy.value = -1; + + return true; + } + + return false; + } +} + export class ToxicAccuracyAttr extends VariableAccuracyAttr { apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { if (user.isOfType(Type.POISON)) { @@ -3235,8 +3259,11 @@ export class FaintCountdownAttr extends AddBattlerTagAttr { } } +/** Attribute used when a move hits a {@link BattlerTagType} for double damage */ export class HitsTagAttr extends MoveAttr { + /** The {@link BattlerTagType} this move hits */ public tagType: BattlerTagType; + /** Should this move deal double damage against {@link HitsTagAttr.tagType}? */ public doubleDamage: boolean; constructor(tagType: BattlerTagType, doubleDamage?: boolean) { @@ -4403,6 +4430,8 @@ export function initMoves() { new AttackMove(Moves.SLAM, Type.NORMAL, MoveCategory.PHYSICAL, 80, 75, 20, -1, 0, 1), new AttackMove(Moves.VINE_WHIP, Type.GRASS, MoveCategory.PHYSICAL, 45, 100, 25, -1, 0, 1), new AttackMove(Moves.STOMP, Type.NORMAL, MoveCategory.PHYSICAL, 65, 100, 20, 30, 0, 1) + .attr(MinimizeAccuracyAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .attr(FlinchAttr), new AttackMove(Moves.DOUBLE_KICK, Type.FIGHTING, MoveCategory.PHYSICAL, 30, 100, 30, -1, 0, 1) .attr(MultiHitAttr, MultiHitType._2), @@ -4426,6 +4455,8 @@ export function initMoves() { .attr(OneHitKOAccuracyAttr), new AttackMove(Moves.TACKLE, Type.NORMAL, MoveCategory.PHYSICAL, 40, 100, 35, -1, 0, 1), new AttackMove(Moves.BODY_SLAM, Type.NORMAL, MoveCategory.PHYSICAL, 85, 100, 15, 30, 0, 1) + .attr(MinimizeAccuracyAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .attr(StatusEffectAttr, StatusEffect.PARALYSIS), new AttackMove(Moves.WRAP, Type.NORMAL, MoveCategory.PHYSICAL, 15, 90, 20, 100, 0, 1) .attr(TrapAttr, BattlerTagType.WRAP), @@ -4623,6 +4654,7 @@ export function initMoves() { new SelfStatusMove(Moves.HARDEN, Type.NORMAL, -1, 30, -1, 0, 1) .attr(StatChangeAttr, BattleStat.DEF, 1, true), new SelfStatusMove(Moves.MINIMIZE, Type.NORMAL, -1, 10, -1, 0, 1) + .attr(AddBattlerTagAttr, BattlerTagType.MINIMIZED, true, false) .attr(StatChangeAttr, BattleStat.EVA, 2, true), new StatusMove(Moves.SMOKESCREEN, Type.NORMAL, 100, 20, -1, 0, 1) .attr(StatChangeAttr, BattleStat.ACC, -1), @@ -5073,7 +5105,7 @@ export function initMoves() { new AttackMove(Moves.FACADE, Type.NORMAL, MoveCategory.PHYSICAL, 70, 100, 20, -1, 0, 3) .attr(MovePowerMultiplierAttr, (user, target, move) => user.status && (user.status.effect === StatusEffect.BURN || user.status.effect === StatusEffect.POISON || user.status.effect === StatusEffect.TOXIC || user.status.effect === StatusEffect.PARALYSIS) ? 2 : 1) - .attr(BypassBurnDamageReductionAttr), + .attr(BypassBurnDamageReductionAttr), new AttackMove(Moves.FOCUS_PUNCH, Type.FIGHTING, MoveCategory.PHYSICAL, 150, 100, 20, -1, -3, 3) .punchingMove() .ignoresVirtual() @@ -5462,6 +5494,8 @@ export function initMoves() { new AttackMove(Moves.DRAGON_PULSE, Type.DRAGON, MoveCategory.SPECIAL, 85, 100, 10, -1, 0, 4) .pulseMove(), new AttackMove(Moves.DRAGON_RUSH, Type.DRAGON, MoveCategory.PHYSICAL, 100, 75, 10, 20, 0, 4) + .attr(MinimizeAccuracyAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .attr(FlinchAttr), new AttackMove(Moves.POWER_GEM, Type.ROCK, MoveCategory.SPECIAL, 80, 100, 20, -1, 0, 4), new AttackMove(Moves.DRAIN_PUNCH, Type.FIGHTING, MoveCategory.PHYSICAL, 75, 100, 10, -1, 0, 4) @@ -5671,7 +5705,9 @@ export function initMoves() { .attr(StatChangeAttr, [ BattleStat.SPATK, BattleStat.SPDEF, BattleStat.SPD ], 1, true) .danceMove(), new AttackMove(Moves.HEAVY_SLAM, Type.STEEL, MoveCategory.PHYSICAL, -1, 100, 10, -1, 0, 5) + .attr(MinimizeAccuracyAttr) .attr(CompareWeightPowerAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .condition(failOnMaxCondition), new AttackMove(Moves.SYNCHRONOISE, Type.PSYCHIC, MoveCategory.SPECIAL, 120, 100, 10, -1, 0, 5) .target(MoveTarget.ALL_NEAR_OTHERS) @@ -5802,7 +5838,9 @@ export function initMoves() { .attr(StatChangeAttr, BattleStat.DEF, -1) .slicingMove(), new AttackMove(Moves.HEAT_CRASH, Type.FIRE, MoveCategory.PHYSICAL, -1, 100, 10, -1, 0, 5) + .attr(MinimizeAccuracyAttr) .attr(CompareWeightPowerAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .condition(failOnMaxCondition), new AttackMove(Moves.LEAF_TORNADO, Type.GRASS, MoveCategory.SPECIAL, 65, 90, 10, 50, 0, 5) .attr(StatChangeAttr, BattleStat.ACC, -1), @@ -5873,7 +5911,9 @@ export function initMoves() { .makesContact(false) .partial(), new AttackMove(Moves.FLYING_PRESS, Type.FIGHTING, MoveCategory.PHYSICAL, 100, 95, 10, -1, 0, 6) + .attr(MinimizeAccuracyAttr) .attr(FlyingTypeMultiplierAttr) + .attr(HitsTagAttr, BattlerTagType.MINIMIZED, true) .condition(failOnGravityCondition), new StatusMove(Moves.MAT_BLOCK, Type.FIGHTING, -1, 10, -1, 0, 6) .unimplemented(), diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index 97d94bdba7c..48287cf39cb 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -1544,6 +1544,12 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { applyPreAttackAbAttrs(DamageBoostAbAttr, source, this, battlerMove, damage); + /** + * For each {@link HitsTagAttr} the move has, doubles the damage of the move if: + * The target has a {@link BattlerTagType} that this move interacts with + * AND + * The move doubles damage when used against that tag + * */ move.getAttrs(HitsTagAttr).map(hta => hta as HitsTagAttr).filter(hta => hta.doubleDamage).forEach(hta => { if (this.getTag(hta.tagType)) damage.value *= 2; From 0b75a5210aea737e18acbbadfe3013fed30136df Mon Sep 17 00:00:00 2001 From: Frederico Santos Date: Wed, 15 May 2024 13:41:40 +0100 Subject: [PATCH 02/46] Implemented Power Split and Guard Split (#699) * Implemented Power Split and Guard Split * Update changeStat method to use summonData for Pokemon stats This commit modifies the `changeStat` method in the `Pokemon` class to use the `summonData` object for updating Pokemon stats instead of directly modifying the `stats` object. This change ensures that the updated stats are correctly reflected in the `summonData` object, which is used for battle calculations and other related operations. Refactor the `getStat` method to check if `summonData` exists and return the corresponding stat value from `summonData.stats` if it does. Otherwise, return the stat value from the `stats` object. This change improves the accuracy of stat calculations during battles and ensures consistency between the `stats` and `summonData` objects. * Added documentation for Power Split and Guard Split + linting * removed incorrect files * Removed incorrect folder * removed unnecessary import * Added documentation for getStat and changeSummonStat methods * New description for getStat() * Adjusting function descriptions * adjusted descriptions according to guideline --------- Co-authored-by: Frederico Santos --- src/data/move.ts | 84 +++++++++++++++++++++++++++++++++++++- src/field/pokemon.ts | 22 +++++++++- src/system/pokemon-data.ts | 1 + 3 files changed, 104 insertions(+), 3 deletions(-) diff --git a/src/data/move.ts b/src/data/move.ts index 46216eb754a..aa722b29e5d 100644 --- a/src/data/move.ts +++ b/src/data/move.ts @@ -2005,6 +2005,86 @@ export class HpSplitAttr extends MoveEffectAttr { } } +/** + * Attribute used for moves which split the user and the target's offensive raw stats. + * @extends MoveEffectAttr + * @see {@link apply} +*/ +export class PowerSplitAttr extends MoveEffectAttr { + + /** + * Applying Power Split to the user and the target. + * @param user The pokemon using the move. {@link Pokemon} + * @param target The targeted pokemon of the move. {@link Pokemon} + * @param move The move used. {@link Move} + * @param args N/A + * @returns True if power split is applied successfully. + */ + apply(user: Pokemon, target: Pokemon, move: Move, args: any[]) : Promise { + return new Promise(resolve => { + + if (!super.apply(user, target, move, args)) + return resolve(false); + + const infoUpdates = []; + + const attackValue = Math.floor((target.getStat(Stat.ATK) + user.getStat(Stat.ATK)) / 2); + user.changeSummonStat(Stat.ATK, attackValue); + infoUpdates.push(user.updateInfo()); + target.changeSummonStat(Stat.ATK, attackValue); + infoUpdates.push(target.updateInfo()); + + const specialAttackValue = Math.floor((target.getStat(Stat.SPATK) + user.getStat(Stat.SPATK)) / 2); + user.changeSummonStat(Stat.SPATK, specialAttackValue); + infoUpdates.push(user.updateInfo()); + target.changeSummonStat(Stat.SPATK, specialAttackValue); + infoUpdates.push(target.updateInfo()); + + return Promise.all(infoUpdates).then(() => resolve(true)); + }); + } +} + +/** + * Attribute used for moves which split the user and the target's defensive raw stats. + * @extends MoveEffectAttr + * @see {@link apply} +*/ +export class GuardSplitAttr extends MoveEffectAttr { + /** + * Applying Guard Split to the user and the target. + * @param user The pokemon using the move. {@link Pokemon} + * @param target The targeted pokemon of the move. {@link Pokemon} + * @param move The move used. {@link Move} + * @param args N/A + * @returns True if power split is applied successfully. + */ + apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): Promise { + return new Promise(resolve => { + if (!super.apply(user, target, move, args)) + return resolve(false); + + const infoUpdates = []; + + const defenseValue = Math.floor((target.getStat(Stat.DEF) + user.getStat(Stat.DEF)) / 2); + user.changeSummonStat(Stat.DEF, defenseValue); + infoUpdates.push(user.updateInfo()); + target.changeSummonStat(Stat.DEF, defenseValue); + infoUpdates.push(target.updateInfo()); + + const specialDefenseValue = Math.floor((target.getStat(Stat.SPDEF) + user.getStat(Stat.SPDEF)) / 2); + user.changeSummonStat(Stat.SPDEF, specialDefenseValue); + infoUpdates.push(user.updateInfo()); + target.changeSummonStat(Stat.SPDEF, specialDefenseValue); + infoUpdates.push(target.updateInfo()); + + + return Promise.all(infoUpdates).then(() => resolve(true)); + }); + } + +} + export class VariablePowerAttr extends MoveAttr { apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { //const power = args[0] as Utils.NumberHolder; @@ -5664,9 +5744,9 @@ export function initMoves() { .target(MoveTarget.USER_SIDE) .unimplemented(), new StatusMove(Moves.GUARD_SPLIT, Type.PSYCHIC, -1, 10, -1, 0, 5) - .unimplemented(), + .attr(GuardSplitAttr), new StatusMove(Moves.POWER_SPLIT, Type.PSYCHIC, -1, 10, -1, 0, 5) - .unimplemented(), + .attr(PowerSplitAttr), new StatusMove(Moves.WONDER_ROOM, Type.PSYCHIC, -1, 10, -1, 0, 5) .ignoresProtect() .target(MoveTarget.BOTH_SIDES) diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index 48287cf39cb..8d6b11ae9f5 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -544,8 +544,17 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { }); } + /** + * Returns the value of the specified stat. + * @param stat Stat to get the value of. {@link Stat} + * @returns The value of the stat. If the pokemon is already summoned, it uses those values, otherwise uses the base stats. + */ getStat(stat: Stat): integer { - return this.stats[stat]; + if (!this.summonData) { + return this.stats[stat]; + } + + return this.summonData.stats[stat]; } getBattleStat(stat: Stat, opponent?: Pokemon, move?: Move, isCritical: boolean = false): integer { @@ -1708,6 +1717,16 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { return healAmount; } + /** + * Sets a specific stat to a specific value. + * Used for summon data, while the pokemon is out until the next time it is retrieved. + * @param stat Stat to change. {@link Stat} + * @param value Amount to set the stat to. + */ + changeSummonStat(stat: Stat, value: integer) : void { + this.summonData.stats[stat] = value; + } + isBossImmune(): boolean { return this.isBoss(); } @@ -2166,6 +2185,7 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { if (!this.battleData) this.resetBattleData(); this.resetBattleSummonData(); + this.summonData.stats = this.stats; if (this.summonDataPrimer) { for (let k of Object.keys(this.summonData)) { if (this.summonDataPrimer[k]) diff --git a/src/system/pokemon-data.ts b/src/system/pokemon-data.ts index dfbb9be570b..dcf4a5744b6 100644 --- a/src/system/pokemon-data.ts +++ b/src/system/pokemon-data.ts @@ -112,6 +112,7 @@ export default class PokemonData { this.summonData = new PokemonSummonData(); if (!forHistory && source.summonData) { this.summonData.battleStats = source.summonData.battleStats; + this.summonData.stats = source.summonData.stats; this.summonData.moveQueue = source.summonData.moveQueue; this.summonData.disabledMove = source.summonData.disabledMove; this.summonData.disabledTurns = source.summonData.disabledTurns; From 58e59369edb584829cac2d900abf90e71836ab7c Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 09:12:03 -0400 Subject: [PATCH 03/46] Revert "Readded removed args, inverted 'simulated' instead of removing (#874)" This reverts commit e89dbad5f1b0ac284a83fbe077f9e708ea850575. --- src/data/ability.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/data/ability.ts b/src/data/ability.ts index 4128f22e2c0..0ff03ed6776 100644 --- a/src/data/ability.ts +++ b/src/data/ability.ts @@ -1755,7 +1755,7 @@ export class StatusEffectImmunityAbAttr extends PreSetStatusAbAttr { } getTriggerMessage(pokemon: Pokemon, abilityName: string, ...args: any[]): string { - return getPokemonMessage(pokemon, `'s ${abilityName}\nprevents ${this.immuneEffects.length ? getStatusEffectDescriptor(this.immuneEffects[0]) : 'status problems'}!`); + return getPokemonMessage(pokemon, `'s ${abilityName}\nprevents ${this.immuneEffects.length ? getStatusEffectDescriptor(args[0] as StatusEffect) : 'status problems'}!`); } } @@ -2825,7 +2825,7 @@ export function applyPostStatChangeAbAttrs(attrType: { new(...args: any[]): Post export function applyPreSetStatusAbAttrs(attrType: { new(...args: any[]): PreSetStatusAbAttr }, pokemon: Pokemon, effect: StatusEffect, cancelled: Utils.BooleanHolder, ...args: any[]): Promise { const simulated = args.length > 1 && args[1]; - return applyAbAttrsInternal(attrType, pokemon, (attr, passive) => attr.applyPreSetStatus(pokemon, passive, effect, cancelled, args), args, false, false, simulated); + return applyAbAttrsInternal(attrType, pokemon, (attr, passive) => attr.applyPreSetStatus(pokemon, passive, effect, cancelled, args), args, false, false, !simulated); } export function applyPreApplyBattlerTagAbAttrs(attrType: { new(...args: any[]): PreApplyBattlerTagAbAttr }, From 5f3fd17fddea2f03d4c1491ef61f52627a361c29 Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 09:42:45 -0400 Subject: [PATCH 04/46] Add Quick Claw item --- public/images/items.json | 6355 ++++++++++++++-------------- public/images/items.png | Bin 50853 -> 51675 bytes public/images/items/quick_claw.png | Bin 0 -> 217 bytes src/modifier/modifier-type.ts | 6 + src/modifier/modifier.ts | 34 + src/phases.ts | 13 +- 6 files changed, 3240 insertions(+), 3168 deletions(-) create mode 100644 public/images/items/quick_claw.png diff --git a/public/images/items.json b/public/images/items.json index 939b3927e7a..05f715ff078 100644 --- a/public/images/items.json +++ b/public/images/items.json @@ -4,8 +4,8 @@ "image": "items.png", "format": "RGBA8888", "size": { - "w": 396, - "h": 396 + "w": 399, + "h": 399 }, "scale": 1, "frames": [ @@ -555,6 +555,27 @@ "h": 20 } }, + { + "filename": "lure", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 4, + "w": 17, + "h": 24 + }, + "frame": { + "x": 382, + "y": 0, + "w": 17, + "h": 24 + } + }, { "filename": "catching_charm", "rotated": false, @@ -703,7 +724,7 @@ } }, { - "filename": "mega_bracelet", + "filename": "coupon", "rotated": false, "trimmed": true, "sourceSize": { @@ -711,20 +732,20 @@ "h": 32 }, "spriteSourceSize": { - "x": 6, - "y": 8, - "w": 20, - "h": 16 + "x": 4, + "y": 7, + "w": 23, + "h": 19 }, "frame": { "x": 0, "y": 380, - "w": 20, - "h": 16 + "w": 23, + "h": 19 } }, { - "filename": "relic_band", + "filename": "golden_mystic_ticket", "rotated": false, "trimmed": true, "sourceSize": { @@ -732,16 +753,16 @@ "h": 32 }, "spriteSourceSize": { - "x": 7, - "y": 9, - "w": 17, - "h": 16 + "x": 4, + "y": 7, + "w": 23, + "h": 19 }, "frame": { - "x": 20, + "x": 23, "y": 380, - "w": 17, - "h": 16 + "w": 23, + "h": 19 } }, { @@ -1039,7 +1060,7 @@ } }, { - "filename": "elixir", + "filename": "oval_charm", "rotated": false, "trimmed": true, "sourceSize": { @@ -1047,15 +1068,15 @@ "h": 32 }, "spriteSourceSize": { - "x": 7, + "x": 6, "y": 4, - "w": 18, + "w": 21, "h": 24 }, "frame": { "x": 378, - "y": 20, - "w": 18, + "y": 24, + "w": 21, "h": 24 } }, @@ -1102,7 +1123,7 @@ } }, { - "filename": "oval_charm", + "filename": "red_orb", "rotated": false, "trimmed": true, "sourceSize": { @@ -1112,13 +1133,13 @@ "spriteSourceSize": { "x": 6, "y": 4, - "w": 21, + "w": 20, "h": 24 }, "frame": { "x": 24, "y": 224, - "w": 21, + "w": 20, "h": 24 } }, @@ -1228,7 +1249,7 @@ } }, { - "filename": "abomasite", + "filename": "mega_bracelet", "rotated": false, "trimmed": true, "sourceSize": { @@ -1236,83 +1257,20 @@ "h": 32 }, "spriteSourceSize": { - "x": 8, + "x": 6, "y": 8, - "w": 16, + "w": 20, "h": 16 }, "frame": { "x": 24, "y": 364, - "w": 16, + "w": 20, "h": 16 } }, { - "filename": "absolite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 37, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "aerodactylite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 40, - "y": 364, - "w": 16, - "h": 16 - } - }, - { - "filename": "aggronite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 53, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "ether", + "filename": "elixir", "rotated": false, "trimmed": true, "sourceSize": { @@ -1333,7 +1291,7 @@ } }, { - "filename": "full_restore", + "filename": "ether", "rotated": false, "trimmed": true, "sourceSize": { @@ -1354,7 +1312,7 @@ } }, { - "filename": "max_elixir", + "filename": "full_restore", "rotated": false, "trimmed": true, "sourceSize": { @@ -1417,7 +1375,7 @@ } }, { - "filename": "max_ether", + "filename": "max_elixir", "rotated": false, "trimmed": true, "sourceSize": { @@ -1438,7 +1396,7 @@ } }, { - "filename": "hp_up", + "filename": "max_ether", "rotated": false, "trimmed": true, "sourceSize": { @@ -1446,20 +1404,20 @@ "h": 32 }, "spriteSourceSize": { - "x": 8, + "x": 7, "y": 4, - "w": 16, + "w": 18, "h": 24 }, "frame": { - "x": 45, + "x": 44, "y": 224, - "w": 16, + "w": 18, "h": 24 } }, { - "filename": "iron", + "filename": "hp_up", "rotated": false, "trimmed": true, "sourceSize": { @@ -1480,7 +1438,7 @@ } }, { - "filename": "lure", + "filename": "iron", "rotated": false, "trimmed": true, "sourceSize": { @@ -1490,13 +1448,13 @@ "spriteSourceSize": { "x": 8, "y": 4, - "w": 17, + "w": 16, "h": 24 }, "frame": { "x": 47, "y": 272, - "w": 17, + "w": 16, "h": 24 } }, @@ -1563,69 +1521,6 @@ "h": 23 } }, - { - "filename": "alakazite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 56, - "y": 364, - "w": 16, - "h": 16 - } - }, - { - "filename": "altarianite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 69, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "revive", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 10, - "y": 8, - "w": 12, - "h": 17 - }, - "frame": { - "x": 382, - "y": 0, - "w": 12, - "h": 17 - } - }, { "filename": "ability_capsule", "rotated": false, @@ -1641,12 +1536,33 @@ "h": 14 }, "frame": { - "x": 138, - "y": 46, + "x": 44, + "y": 364, "w": 24, "h": 14 } }, + { + "filename": "amulet_coin", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 5, + "w": 23, + "h": 21 + }, + "frame": { + "x": 46, + "y": 378, + "w": 23, + "h": 21 + } + }, { "filename": "choice_specs", "rotated": false, @@ -1662,29 +1578,8 @@ "h": 18 }, "frame": { - "x": 162, - "y": 45, - "w": 24, - "h": 18 - } - }, - { - "filename": "dragon_scale", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 8, - "w": 24, - "h": 18 - }, - "frame": { - "x": 186, - "y": 45, + "x": 138, + "y": 46, "w": 24, "h": 18 } @@ -1704,7 +1599,7 @@ "h": 22 }, "frame": { - "x": 210, + "x": 162, "y": 45, "w": 24, "h": 22 @@ -1725,7 +1620,7 @@ "h": 22 }, "frame": { - "x": 234, + "x": 186, "y": 45, "w": 24, "h": 22 @@ -1746,7 +1641,7 @@ "h": 23 }, "frame": { - "x": 258, + "x": 210, "y": 45, "w": 24, "h": 23 @@ -1767,7 +1662,7 @@ "h": 23 }, "frame": { - "x": 282, + "x": 234, "y": 45, "w": 24, "h": 23 @@ -1788,8 +1683,8 @@ "h": 23 }, "frame": { - "x": 306, - "y": 44, + "x": 258, + "y": 45, "w": 24, "h": 23 } @@ -1809,56 +1704,14 @@ "h": 22 }, "frame": { - "x": 330, - "y": 43, + "x": 282, + "y": 45, "w": 24, "h": 22 } }, { - "filename": "healing_charm", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 23, - "h": 22 - }, - "frame": { - "x": 354, - "y": 43, - "w": 23, - "h": 22 - } - }, - { - "filename": "lock_capsule", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 5, - "w": 19, - "h": 22 - }, - "frame": { - "x": 377, - "y": 44, - "w": 19, - "h": 22 - } - }, - { - "filename": "icy_reins_of_unity", + "filename": "rare_candy", "rotated": false, "trimmed": true, "sourceSize": { @@ -1867,141 +1720,15 @@ }, "spriteSourceSize": { "x": 4, - "y": 7, - "w": 24, - "h": 20 - }, - "frame": { - "x": 330, - "y": 65, - "w": 24, - "h": 20 - } - }, - { - "filename": "amulet_coin", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, "y": 5, "w": 23, - "h": 21 - }, - "frame": { - "x": 354, - "y": 65, - "w": 23, - "h": 21 - } - }, - { - "filename": "metal_coat", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 5, - "w": 19, - "h": 22 - }, - "frame": { - "x": 377, - "y": 66, - "w": 19, - "h": 22 - } - }, - { - "filename": "rusted_shield", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 6, - "w": 24, - "h": 20 + "h": 23 }, "frame": { "x": 306, - "y": 67, - "w": 24, - "h": 20 - } - }, - { - "filename": "sacred_ash", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 7, - "w": 24, - "h": 20 - }, - "frame": { - "x": 330, - "y": 85, - "w": 24, - "h": 20 - } - }, - { - "filename": "auspicious_armor", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 5, + "y": 44, "w": 23, - "h": 21 - }, - "frame": { - "x": 354, - "y": 86, - "w": 23, - "h": 21 - } - }, - { - "filename": "spell_tag", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 6, - "w": 19, - "h": 21 - }, - "frame": { - "x": 377, - "y": 88, - "w": 19, - "h": 21 + "h": 23 } }, { @@ -2026,7 +1753,7 @@ } }, { - "filename": "red_orb", + "filename": "super_lure", "rotated": false, "trimmed": true, "sourceSize": { @@ -2034,102 +1761,18 @@ "h": 32 }, "spriteSourceSize": { - "x": 6, + "x": 8, "y": 4, - "w": 20, + "w": 17, "h": 24 }, "frame": { "x": 61, "y": 200, - "w": 20, + "w": 17, "h": 24 } }, - { - "filename": "bug_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 61, - "y": 224, - "w": 22, - "h": 23 - } - }, - { - "filename": "dark_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 63, - "y": 247, - "w": 22, - "h": 23 - } - }, - { - "filename": "dragon_fang", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 21, - "h": 23 - }, - "frame": { - "x": 64, - "y": 270, - "w": 21, - "h": 23 - } - }, - { - "filename": "dragon_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 64, - "y": 293, - "w": 22, - "h": 23 - } - }, { "filename": "max_repel", "rotated": false, @@ -2145,8 +1788,8 @@ "h": 24 }, "frame": { - "x": 70, - "y": 316, + "x": 62, + "y": 224, "w": 16, "h": 24 } @@ -2166,14 +1809,14 @@ "h": 24 }, "frame": { - "x": 70, - "y": 340, + "x": 63, + "y": 248, "w": 16, "h": 24 } }, { - "filename": "ampharosite", + "filename": "pp_up", "rotated": false, "trimmed": true, "sourceSize": { @@ -2182,19 +1825,19 @@ }, "spriteSourceSize": { "x": 8, - "y": 8, + "y": 4, "w": 16, - "h": 16 + "h": 24 }, "frame": { - "x": 72, - "y": 364, + "x": 63, + "y": 272, "w": 16, - "h": 16 + "h": 24 } }, { - "filename": "audinite", + "filename": "protein", "rotated": false, "trimmed": true, "sourceSize": { @@ -2203,15 +1846,225 @@ }, "spriteSourceSize": { "x": 8, - "y": 8, + "y": 4, "w": 16, - "h": 16 + "h": 24 }, "frame": { - "x": 85, - "y": 380, + "x": 64, + "y": 296, "w": 16, - "h": 16 + "h": 24 + } + }, + { + "filename": "repel", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 4, + "w": 16, + "h": 24 + }, + "frame": { + "x": 70, + "y": 320, + "w": 16, + "h": 24 + } + }, + { + "filename": "apicot_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 19, + "h": 20 + }, + "frame": { + "x": 70, + "y": 344, + "w": 19, + "h": 20 + } + }, + { + "filename": "bug_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 69, + "y": 364, + "w": 22, + "h": 23 + } + }, + { + "filename": "relic_gold", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 9, + "y": 11, + "w": 15, + "h": 11 + }, + "frame": { + "x": 69, + "y": 387, + "w": 15, + "h": 11 + } + }, + { + "filename": "dragon_scale", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 8, + "w": 24, + "h": 18 + }, + "frame": { + "x": 330, + "y": 43, + "w": 24, + "h": 18 + } + }, + { + "filename": "icy_reins_of_unity", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 7, + "w": 24, + "h": 20 + }, + "frame": { + "x": 354, + "y": 43, + "w": 24, + "h": 20 + } + }, + { + "filename": "dragon_fang", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 21, + "h": 23 + }, + "frame": { + "x": 378, + "y": 48, + "w": 21, + "h": 23 + } + }, + { + "filename": "rusted_shield", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 6, + "w": 24, + "h": 20 + }, + "frame": { + "x": 329, + "y": 61, + "w": 24, + "h": 20 + } + }, + { + "filename": "sacred_ash", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 7, + "w": 24, + "h": 20 + }, + "frame": { + "x": 353, + "y": 63, + "w": 24, + "h": 20 + } + }, + { + "filename": "dark_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 377, + "y": 71, + "w": 22, + "h": 23 } }, { @@ -2256,6 +2109,27 @@ "h": 20 } }, + { + "filename": "auspicious_armor", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 5, + "w": 23, + "h": 21 + }, + "frame": { + "x": 115, + "y": 50, + "w": 23, + "h": 21 + } + }, { "filename": "binding_band", "rotated": false, @@ -2271,8 +2145,8 @@ "h": 20 }, "frame": { - "x": 115, - "y": 50, + "x": 138, + "y": 64, "w": 23, "h": 20 } @@ -2292,8 +2166,8 @@ "h": 17 }, "frame": { - "x": 138, - "y": 60, + "x": 161, + "y": 67, "w": 23, "h": 17 } @@ -2313,8 +2187,8 @@ "h": 17 }, "frame": { - "x": 161, - "y": 63, + "x": 184, + "y": 67, "w": 23, "h": 17 } @@ -2334,14 +2208,14 @@ "h": 17 }, "frame": { - "x": 184, - "y": 63, + "x": 207, + "y": 68, "w": 23, "h": 17 } }, { - "filename": "coupon", + "filename": "douse_drive", "rotated": false, "trimmed": true, "sourceSize": { @@ -2350,36 +2224,99 @@ }, "spriteSourceSize": { "x": 4, - "y": 7, + "y": 8, "w": 23, - "h": 19 - }, - "frame": { - "x": 207, - "y": 67, - "w": 23, - "h": 19 - } - }, - { - "filename": "golden_mystic_ticket", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 7, - "w": 23, - "h": 19 + "h": 17 }, "frame": { "x": 230, + "y": 68, + "w": 23, + "h": 17 + } + }, + { + "filename": "healing_charm", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 23, + "h": 22 + }, + "frame": { + "x": 253, + "y": 68, + "w": 23, + "h": 22 + } + }, + { + "filename": "berry_pot", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 5, + "w": 18, + "h": 22 + }, + "frame": { + "x": 276, + "y": 68, + "w": 18, + "h": 22 + } + }, + { + "filename": "rarer_candy", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 5, + "w": 23, + "h": 23 + }, + "frame": { + "x": 294, "y": 67, "w": 23, - "h": 19 + "h": 23 + } + }, + { + "filename": "revive", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 10, + "y": 8, + "w": 12, + "h": 17 + }, + "frame": { + "x": 317, + "y": 67, + "w": 12, + "h": 17 } }, { @@ -2397,8 +2334,8 @@ "h": 21 }, "frame": { - "x": 253, - "y": 68, + "x": 60, + "y": 70, "w": 23, "h": 21 } @@ -2418,73 +2355,10 @@ "h": 21 }, "frame": { - "x": 276, - "y": 68, - "w": 23, - "h": 21 - } - }, - { - "filename": "douse_drive", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 8, - "w": 23, - "h": 17 - }, - "frame": { - "x": 60, + "x": 83, "y": 70, "w": 23, - "h": 17 - } - }, - { - "filename": "rare_candy", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 5, - "w": 23, - "h": 23 - }, - "frame": { - "x": 57, - "y": 87, - "w": 23, - "h": 23 - } - }, - { - "filename": "rarer_candy", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 5, - "w": 23, - "h": 23 - }, - "frame": { - "x": 57, - "y": 110, - "w": 23, - "h": 23 + "h": 21 } }, { @@ -2503,13 +2377,13 @@ }, "frame": { "x": 57, - "y": 133, + "y": 91, "w": 23, "h": 23 } }, { - "filename": "apicot_berry", + "filename": "dragon_tera_shard", "rotated": false, "trimmed": true, "sourceSize": { @@ -2518,36 +2392,15 @@ }, "spriteSourceSize": { "x": 6, - "y": 6, - "w": 19, - "h": 20 + "y": 4, + "w": 22, + "h": 23 }, "frame": { - "x": 63, - "y": 156, - "w": 19, - "h": 20 - } - }, - { - "filename": "mystic_ticket", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 7, - "w": 23, - "h": 19 - }, - "frame": { - "x": 83, - "y": 70, - "w": 23, - "h": 19 + "x": 80, + "y": 91, + "w": 22, + "h": 23 } }, { @@ -2565,12 +2418,33 @@ "h": 23 }, "frame": { - "x": 80, - "y": 89, + "x": 57, + "y": 114, "w": 22, "h": 23 } }, + { + "filename": "super_repel", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 4, + "w": 16, + "h": 24 + }, + "frame": { + "x": 57, + "y": 137, + "w": 16, + "h": 24 + } + }, { "filename": "fairy_tera_shard", "rotated": false, @@ -2586,14 +2460,14 @@ "h": 23 }, "frame": { - "x": 80, - "y": 112, + "x": 79, + "y": 114, "w": 22, "h": 23 } }, { - "filename": "deep_sea_tooth", + "filename": "fighting_tera_shard", "rotated": false, "trimmed": true, "sourceSize": { @@ -2601,16 +2475,58 @@ "h": 32 }, "spriteSourceSize": { - "x": 5, - "y": 6, + "x": 6, + "y": 4, "w": 22, - "h": 21 + "h": 23 }, "frame": { - "x": 80, - "y": 135, + "x": 73, + "y": 137, "w": 22, - "h": 21 + "h": 23 + } + }, + { + "filename": "candy_overlay", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 12, + "w": 16, + "h": 15 + }, + "frame": { + "x": 63, + "y": 161, + "w": 16, + "h": 15 + } + }, + { + "filename": "unknown", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 4, + "w": 16, + "h": 24 + }, + "frame": { + "x": 79, + "y": 160, + "w": 16, + "h": 24 } }, { @@ -2629,13 +2545,13 @@ }, "frame": { "x": 106, - "y": 70, + "y": 71, "w": 23, "h": 21 } }, { - "filename": "fighting_tera_shard", + "filename": "rusted_sword", "rotated": false, "trimmed": true, "sourceSize": { @@ -2643,16 +2559,16 @@ "h": 32 }, "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 + "x": 4, + "y": 5, + "w": 23, + "h": 22 }, "frame": { "x": 102, - "y": 91, - "w": 22, - "h": 23 + "y": 92, + "w": 23, + "h": 22 } }, { @@ -2670,54 +2586,12 @@ "h": 23 }, "frame": { - "x": 102, + "x": 101, "y": 114, "w": 22, "h": 23 } }, - { - "filename": "blunder_policy", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 19 - }, - "frame": { - "x": 102, - "y": 137, - "w": 22, - "h": 19 - } - }, - { - "filename": "reviver_seed", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 8, - "w": 23, - "h": 20 - }, - "frame": { - "x": 82, - "y": 156, - "w": 23, - "h": 20 - } - }, { "filename": "fire_tera_shard", "rotated": false, @@ -2733,8 +2607,8 @@ "h": 23 }, "frame": { - "x": 79, - "y": 176, + "x": 95, + "y": 137, "w": 22, "h": 23 } @@ -2754,12 +2628,33 @@ "h": 23 }, "frame": { - "x": 81, - "y": 199, + "x": 95, + "y": 160, "w": 22, "h": 23 } }, + { + "filename": "abomasite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 79, + "y": 184, + "w": 16, + "h": 16 + } + }, { "filename": "focus_sash", "rotated": false, @@ -2775,8 +2670,8 @@ "h": 23 }, "frame": { - "x": 83, - "y": 222, + "x": 78, + "y": 200, "w": 22, "h": 23 } @@ -2796,12 +2691,33 @@ "h": 23 }, "frame": { - "x": 85, - "y": 245, + "x": 78, + "y": 223, "w": 22, "h": 23 } }, + { + "filename": "shock_drive", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 8, + "w": 23, + "h": 17 + }, + "frame": { + "x": 95, + "y": 183, + "w": 23, + "h": 17 + } + }, { "filename": "grass_tera_shard", "rotated": false, @@ -2817,8 +2733,8 @@ "h": 23 }, "frame": { - "x": 85, - "y": 268, + "x": 79, + "y": 246, "w": 22, "h": 23 } @@ -2838,8 +2754,8 @@ "h": 23 }, "frame": { - "x": 86, - "y": 291, + "x": 79, + "y": 269, "w": 22, "h": 23 } @@ -2859,8 +2775,8 @@ "h": 23 }, "frame": { - "x": 86, - "y": 314, + "x": 100, + "y": 200, "w": 22, "h": 23 } @@ -2880,92 +2796,8 @@ "h": 23 }, "frame": { - "x": 86, - "y": 337, - "w": 22, - "h": 23 - } - }, - { - "filename": "big_nugget", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 20, - "h": 20 - }, - "frame": { - "x": 88, - "y": 360, - "w": 20, - "h": 20 - } - }, - { - "filename": "banettite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 101, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "blue_orb", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 20, - "h": 20 - }, - "frame": { - "x": 105, - "y": 156, - "w": 20, - "h": 20 - } - }, - { - "filename": "normal_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 101, - "y": 176, + "x": 100, + "y": 223, "w": 22, "h": 23 } @@ -2985,8 +2817,8 @@ "h": 23 }, "frame": { - "x": 103, - "y": 199, + "x": 101, + "y": 246, "w": 21, "h": 23 } @@ -3006,12 +2838,33 @@ "h": 23 }, "frame": { - "x": 105, - "y": 222, + "x": 101, + "y": 269, "w": 21, "h": 23 } }, + { + "filename": "normal_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 80, + "y": 292, + "w": 22, + "h": 23 + } + }, { "filename": "mystic_water", "rotated": false, @@ -3027,8 +2880,8 @@ "h": 23 }, "frame": { - "x": 107, - "y": 245, + "x": 102, + "y": 292, "w": 20, "h": 23 } @@ -3048,12 +2901,33 @@ "h": 23 }, "frame": { - "x": 107, - "y": 268, + "x": 86, + "y": 315, "w": 22, "h": 23 } }, + { + "filename": "full_heal", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 9, + "y": 4, + "w": 15, + "h": 23 + }, + "frame": { + "x": 108, + "y": 315, + "w": 15, + "h": 23 + } + }, { "filename": "poison_tera_shard", "rotated": false, @@ -3069,8 +2943,8 @@ "h": 23 }, "frame": { - "x": 108, - "y": 291, + "x": 89, + "y": 338, "w": 22, "h": 23 } @@ -3090,56 +2964,14 @@ "h": 23 }, "frame": { - "x": 108, - "y": 314, + "x": 91, + "y": 361, "w": 22, "h": 23 } }, { - "filename": "reaper_cloth", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 23 - }, - "frame": { - "x": 108, - "y": 337, - "w": 22, - "h": 23 - } - }, - { - "filename": "deep_sea_scale", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 20 - }, - "frame": { - "x": 108, - "y": 360, - "w": 22, - "h": 20 - } - }, - { - "filename": "beedrillite", + "filename": "hyper_potion", "rotated": false, "trimmed": true, "sourceSize": { @@ -3148,246 +2980,78 @@ }, "spriteSourceSize": { "x": 8, + "y": 5, + "w": 17, + "h": 23 + }, + "frame": { + "x": 111, + "y": 338, + "w": 17, + "h": 23 + } + }, + { + "filename": "potion", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 5, + "w": 17, + "h": 23 + }, + "frame": { + "x": 113, + "y": 361, + "w": 17, + "h": 23 + } + }, + { + "filename": "prism_scale", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 9, "y": 8, + "w": 15, + "h": 15 + }, + "frame": { + "x": 91, + "y": 384, + "w": 15, + "h": 15 + } + }, + { + "filename": "zinc", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 4, "w": 16, - "h": 16 + "h": 24 }, "frame": { "x": 117, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "pp_up", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, + "y": 137, "w": 16, "h": 24 - }, - "frame": { - "x": 124, - "y": 91, - "w": 16, - "h": 24 - } - }, - { - "filename": "protein", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 16, - "h": 24 - }, - "frame": { - "x": 124, - "y": 115, - "w": 16, - "h": 24 - } - }, - { - "filename": "everstone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 8, - "w": 20, - "h": 17 - }, - "frame": { - "x": 124, - "y": 139, - "w": 20, - "h": 17 - } - }, - { - "filename": "candy_jar", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 19, - "h": 20 - }, - "frame": { - "x": 125, - "y": 156, - "w": 19, - "h": 20 - } - }, - { - "filename": "rock_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 123, - "y": 176, - "w": 22, - "h": 23 - } - }, - { - "filename": "sharp_beak", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 21, - "h": 23 - }, - "frame": { - "x": 124, - "y": 199, - "w": 21, - "h": 23 - } - }, - { - "filename": "steel_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 126, - "y": 222, - "w": 22, - "h": 23 - } - }, - { - "filename": "stellar_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 127, - "y": 245, - "w": 22, - "h": 23 - } - }, - { - "filename": "water_tera_shard", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 129, - "y": 268, - "w": 22, - "h": 23 - } - }, - { - "filename": "whipped_dream", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 4, - "w": 21, - "h": 23 - }, - "frame": { - "x": 130, - "y": 291, - "w": 21, - "h": 23 - } - }, - { - "filename": "wide_lens", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 4, - "w": 22, - "h": 23 - }, - "frame": { - "x": 130, - "y": 314, - "w": 22, - "h": 23 } }, { @@ -3405,533 +3069,8 @@ "h": 22 }, "frame": { - "x": 130, - "y": 337, - "w": 22, - "h": 22 - } - }, - { - "filename": "liechi_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 21 - }, - "frame": { - "x": 130, - "y": 359, - "w": 22, - "h": 21 - } - }, - { - "filename": "blastoisinite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 133, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "blazikenite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 149, - "y": 380, - "w": 16, - "h": 16 - } - }, - { - "filename": "dusk_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 21, - "h": 21 - }, - "frame": { - "x": 140, - "y": 77, - "w": 21, - "h": 21 - } - }, - { - "filename": "dire_hit", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 140, - "y": 98, - "w": 22, - "h": 22 - } - }, - { - "filename": "dubious_disc", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 22, - "h": 19 - }, - "frame": { - "x": 140, - "y": 120, - "w": 22, - "h": 19 - } - }, - { - "filename": "relic_crown", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 7, - "w": 23, - "h": 18 - }, - "frame": { - "x": 161, - "y": 80, - "w": 23, - "h": 18 - } - }, - { - "filename": "pair_of_tickets", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 7, - "w": 23, - "h": 19 - }, - "frame": { - "x": 184, - "y": 80, - "w": 23, - "h": 19 - } - }, - { - "filename": "dna_splicers", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 162, - "y": 98, - "w": 22, - "h": 22 - } - }, - { - "filename": "rusted_sword", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 5, - "w": 23, - "h": 22 - }, - "frame": { - "x": 184, - "y": 99, - "w": 23, - "h": 22 - } - }, - { - "filename": "electirizer", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 207, - "y": 86, - "w": 22, - "h": 22 - } - }, - { - "filename": "enigma_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 229, - "y": 86, - "w": 22, - "h": 22 - } - }, - { - "filename": "fairy_feather", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 22, - "h": 20 - }, - "frame": { - "x": 162, - "y": 120, - "w": 22, - "h": 20 - } - }, - { - "filename": "sachet", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 4, - "w": 18, - "h": 23 - }, - "frame": { - "x": 144, - "y": 139, - "w": 18, - "h": 23 - } - }, - { - "filename": "ganlon_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 162, - "y": 140, - "w": 22, - "h": 22 - } - }, - { - "filename": "guard_spec", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 184, - "y": 121, - "w": 22, - "h": 22 - } - }, - { - "filename": "ice_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 184, - "y": 143, - "w": 22, - "h": 22 - } - }, - { - "filename": "shell_bell", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 23, - "h": 20 - }, - "frame": { - "x": 251, - "y": 89, - "w": 23, - "h": 20 - } - }, - { - "filename": "wellspring_mask", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 5, - "w": 23, - "h": 21 - }, - "frame": { - "x": 274, - "y": 89, - "w": 23, - "h": 21 - } - }, - { - "filename": "shock_drive", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 4, - "y": 8, - "w": 23, - "h": 17 - }, - "frame": { - "x": 207, - "y": 108, - "w": 23, - "h": 17 - } - }, - { - "filename": "magmarizer", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 206, - "y": 125, - "w": 22, - "h": 22 - } - }, - { - "filename": "malicious_armor", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 20 - }, - "frame": { - "x": 206, - "y": 147, - "w": 22, - "h": 20 - } - }, - { - "filename": "masterpiece_teacup", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 21, - "h": 18 - }, - "frame": { - "x": 230, - "y": 108, - "w": 21, - "h": 18 - } - }, - { - "filename": "memory_bug", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 228, - "y": 126, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_dark", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 228, - "y": 148, + "x": 117, + "y": 161, "w": 22, "h": 22 } @@ -3951,12 +3090,579 @@ "h": 17 }, "frame": { - "x": 251, - "y": 109, + "x": 118, + "y": 183, "w": 23, "h": 17 } }, + { + "filename": "reaper_cloth", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 23 + }, + "frame": { + "x": 122, + "y": 200, + "w": 22, + "h": 23 + } + }, + { + "filename": "rock_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 122, + "y": 223, + "w": 22, + "h": 23 + } + }, + { + "filename": "steel_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 122, + "y": 246, + "w": 22, + "h": 23 + } + }, + { + "filename": "stellar_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 122, + "y": 269, + "w": 22, + "h": 23 + } + }, + { + "filename": "water_tera_shard", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 122, + "y": 292, + "w": 22, + "h": 23 + } + }, + { + "filename": "sharp_beak", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 21, + "h": 23 + }, + "frame": { + "x": 123, + "y": 315, + "w": 21, + "h": 23 + } + }, + { + "filename": "sachet", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 4, + "w": 18, + "h": 23 + }, + "frame": { + "x": 128, + "y": 338, + "w": 18, + "h": 23 + } + }, + { + "filename": "super_potion", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 5, + "w": 17, + "h": 23 + }, + "frame": { + "x": 130, + "y": 361, + "w": 17, + "h": 23 + } + }, + { + "filename": "whipped_dream", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 4, + "w": 21, + "h": 23 + }, + "frame": { + "x": 123, + "y": 114, + "w": 21, + "h": 23 + } + }, + { + "filename": "dire_hit", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 125, + "y": 92, + "w": 22, + "h": 22 + } + }, + { + "filename": "wide_lens", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 4, + "w": 22, + "h": 23 + }, + "frame": { + "x": 147, + "y": 84, + "w": 22, + "h": 23 + } + }, + { + "filename": "dna_splicers", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 169, + "y": 84, + "w": 22, + "h": 22 + } + }, + { + "filename": "leftovers", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 5, + "w": 15, + "h": 22 + }, + "frame": { + "x": 191, + "y": 84, + "w": 15, + "h": 22 + } + }, + { + "filename": "wellspring_mask", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 5, + "w": 23, + "h": 21 + }, + "frame": { + "x": 206, + "y": 85, + "w": 23, + "h": 21 + } + }, + { + "filename": "deep_sea_tooth", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 21 + }, + "frame": { + "x": 229, + "y": 85, + "w": 22, + "h": 21 + } + }, + { + "filename": "mystic_ticket", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 7, + "w": 23, + "h": 19 + }, + "frame": { + "x": 251, + "y": 90, + "w": 23, + "h": 19 + } + }, + { + "filename": "pair_of_tickets", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 7, + "w": 23, + "h": 19 + }, + "frame": { + "x": 274, + "y": 90, + "w": 23, + "h": 19 + } + }, + { + "filename": "big_nugget", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 20, + "h": 20 + }, + "frame": { + "x": 297, + "y": 90, + "w": 20, + "h": 20 + } + }, + { + "filename": "electirizer", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 317, + "y": 84, + "w": 22, + "h": 22 + } + }, + { + "filename": "enigma_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 133, + "y": 137, + "w": 22, + "h": 22 + } + }, + { + "filename": "ganlon_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 139, + "y": 159, + "w": 22, + "h": 22 + } + }, + { + "filename": "blunder_policy", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 19 + }, + "frame": { + "x": 141, + "y": 181, + "w": 22, + "h": 19 + } + }, + { + "filename": "guard_spec", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 144, + "y": 200, + "w": 22, + "h": 22 + } + }, + { + "filename": "ice_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 144, + "y": 222, + "w": 22, + "h": 22 + } + }, + { + "filename": "magmarizer", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 144, + "y": 244, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_bug", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 144, + "y": 266, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_dark", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 144, + "y": 288, + "w": 22, + "h": 22 + } + }, { "filename": "memory_dragon", "rotated": false, @@ -3972,701 +3678,8 @@ "h": 22 }, "frame": { - "x": 250, - "y": 126, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_electric", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 250, - "y": 148, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_fairy", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 274, - "y": 110, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_fighting", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 272, - "y": 132, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_fire", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 272, - "y": 154, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_flying", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 145, - "y": 162, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_ghost", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 145, - "y": 184, - "w": 22, - "h": 22 - } - }, - { - "filename": "super_lure", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 17, - "h": 24 - }, - "frame": { - "x": 167, - "y": 162, - "w": 17, - "h": 24 - } - }, - { - "filename": "memory_grass", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 184, - "y": 165, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_ground", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 206, - "y": 167, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_ice", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 228, - "y": 170, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_normal", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 250, - "y": 170, - "w": 22, - "h": 22 - } - }, - { - "filename": "tm_normal", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 250, - "y": 170, - "w": 22, - "h": 22 - } - }, - { - "filename": "golden_egg", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 6, - "w": 17, - "h": 20 - }, - "frame": { - "x": 167, - "y": 186, - "w": 17, - "h": 20 - } - }, - { - "filename": "memory_poison", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 184, - "y": 187, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_psychic", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 206, - "y": 189, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_rock", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 228, - "y": 192, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_steel", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 250, - "y": 192, - "w": 22, - "h": 22 - } - }, - { - "filename": "memory_water", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 272, - "y": 176, - "w": 22, - "h": 22 - } - }, - { - "filename": "mini_black_hole", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 272, - "y": 198, - "w": 22, - "h": 22 - } - }, - { - "filename": "cameruptite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 145, - "y": 206, - "w": 16, - "h": 16 - } - }, - { - "filename": "protector", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 161, - "y": 206, - "w": 22, - "h": 22 - } - }, - { - "filename": "scroll_of_darkness", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 183, - "y": 209, - "w": 22, - "h": 22 - } - }, - { - "filename": "scroll_of_waters", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 205, - "y": 211, - "w": 22, - "h": 22 - } - }, - { - "filename": "shed_shell", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 227, - "y": 214, - "w": 22, - "h": 22 - } - }, - { - "filename": "starf_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 249, - "y": 214, - "w": 22, - "h": 22 - } - }, - { - "filename": "sweet_apple", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 21 - }, - "frame": { - "x": 271, - "y": 220, - "w": 22, - "h": 21 - } - }, - { - "filename": "repel", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 16, - "h": 24 - }, - "frame": { - "x": 294, - "y": 132, - "w": 16, - "h": 24 - } - }, - { - "filename": "super_repel", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 16, - "h": 24 - }, - "frame": { - "x": 294, - "y": 156, - "w": 16, - "h": 24 - } - }, - { - "filename": "unknown", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 16, - "h": 24 - }, - "frame": { - "x": 294, - "y": 180, - "w": 16, - "h": 24 - } - }, - { - "filename": "dawn_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 20, - "h": 21 - }, - "frame": { - "x": 310, - "y": 87, - "w": 20, - "h": 21 - } - }, - { - "filename": "berry_pot", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 5, - "w": 18, - "h": 22 - }, - "frame": { - "x": 296, - "y": 110, - "w": 18, - "h": 22 - } - }, - { - "filename": "zinc", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 4, - "w": 16, - "h": 24 - }, - "frame": { - "x": 314, - "y": 108, - "w": 16, - "h": 24 - } - }, - { - "filename": "thunder_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 5, - "w": 22, - "h": 22 - }, - "frame": { - "x": 330, - "y": 105, + "x": 144, + "y": 310, "w": 22, "h": 22 } @@ -4686,12 +3699,915 @@ "h": 22 }, "frame": { - "x": 310, - "y": 132, + "x": 146, + "y": 332, "w": 20, "h": 22 } }, + { + "filename": "lock_capsule", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 5, + "w": 19, + "h": 22 + }, + "frame": { + "x": 147, + "y": 354, + "w": 19, + "h": 22 + } + }, + { + "filename": "deep_sea_scale", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 20 + }, + "frame": { + "x": 147, + "y": 107, + "w": 22, + "h": 20 + } + }, + { + "filename": "liechi_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 21 + }, + "frame": { + "x": 169, + "y": 106, + "w": 22, + "h": 21 + } + }, + { + "filename": "memory_electric", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 191, + "y": 106, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_fairy", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 213, + "y": 106, + "w": 22, + "h": 22 + } + }, + { + "filename": "mystery_egg", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 18 + }, + "frame": { + "x": 235, + "y": 106, + "w": 16, + "h": 18 + } + }, + { + "filename": "relic_crown", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 4, + "y": 7, + "w": 23, + "h": 18 + }, + "frame": { + "x": 251, + "y": 109, + "w": 23, + "h": 18 + } + }, + { + "filename": "reviver_seed", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 8, + "w": 23, + "h": 20 + }, + "frame": { + "x": 274, + "y": 109, + "w": 23, + "h": 20 + } + }, + { + "filename": "blue_orb", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 20, + "h": 20 + }, + "frame": { + "x": 297, + "y": 110, + "w": 20, + "h": 20 + } + }, + { + "filename": "memory_fighting", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 317, + "y": 106, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_fire", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 155, + "y": 127, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_flying", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 339, + "y": 83, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_ghost", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 339, + "y": 105, + "w": 22, + "h": 22 + } + }, + { + "filename": "absolite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 361, + "y": 83, + "w": 16, + "h": 16 + } + }, + { + "filename": "memory_grass", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 377, + "y": 94, + "w": 22, + "h": 22 + } + }, + { + "filename": "aerodactylite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 361, + "y": 99, + "w": 16, + "h": 16 + } + }, + { + "filename": "aggronite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 361, + "y": 115, + "w": 16, + "h": 16 + } + }, + { + "filename": "memory_ground", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 377, + "y": 116, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_ice", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 177, + "y": 128, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_normal", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 199, + "y": 128, + "w": 22, + "h": 22 + } + }, + { + "filename": "tm_normal", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 199, + "y": 128, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_poison", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 221, + "y": 128, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_psychic", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 243, + "y": 127, + "w": 22, + "h": 22 + } + }, + { + "filename": "shell_bell", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 23, + "h": 20 + }, + "frame": { + "x": 265, + "y": 129, + "w": 23, + "h": 20 + } + }, + { + "filename": "dubious_disc", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 22, + "h": 19 + }, + "frame": { + "x": 288, + "y": 130, + "w": 22, + "h": 19 + } + }, + { + "filename": "big_mushroom", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 19, + "h": 19 + }, + "frame": { + "x": 147, + "y": 376, + "w": 19, + "h": 19 + } + }, + { + "filename": "fairy_feather", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 22, + "h": 20 + }, + "frame": { + "x": 339, + "y": 127, + "w": 22, + "h": 20 + } + }, + { + "filename": "malicious_armor", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 20 + }, + "frame": { + "x": 317, + "y": 128, + "w": 22, + "h": 20 + } + }, + { + "filename": "alakazite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 361, + "y": 131, + "w": 16, + "h": 16 + } + }, + { + "filename": "memory_rock", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 377, + "y": 138, + "w": 22, + "h": 22 + } + }, + { + "filename": "altarianite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 161, + "y": 149, + "w": 16, + "h": 16 + } + }, + { + "filename": "memory_steel", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 177, + "y": 150, + "w": 22, + "h": 22 + } + }, + { + "filename": "memory_water", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 199, + "y": 150, + "w": 22, + "h": 22 + } + }, + { + "filename": "mini_black_hole", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 221, + "y": 150, + "w": 22, + "h": 22 + } + }, + { + "filename": "protector", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 243, + "y": 149, + "w": 22, + "h": 22 + } + }, + { + "filename": "scroll_of_darkness", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 265, + "y": 149, + "w": 22, + "h": 22 + } + }, + { + "filename": "scroll_of_waters", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 287, + "y": 149, + "w": 22, + "h": 22 + } + }, + { + "filename": "ampharosite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 161, + "y": 165, + "w": 16, + "h": 16 + } + }, + { + "filename": "lum_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 7, + "w": 20, + "h": 19 + }, + "frame": { + "x": 163, + "y": 181, + "w": 20, + "h": 19 + } + }, + { + "filename": "metal_coat", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 5, + "w": 19, + "h": 22 + }, + "frame": { + "x": 166, + "y": 200, + "w": 19, + "h": 22 + } + }, + { + "filename": "shed_shell", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 166, + "y": 222, + "w": 22, + "h": 22 + } + }, + { + "filename": "starf_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 166, + "y": 244, + "w": 22, + "h": 22 + } + }, + { + "filename": "thunder_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 5, + "w": 22, + "h": 22 + }, + "frame": { + "x": 166, + "y": 266, + "w": 22, + "h": 22 + } + }, { "filename": "tm_bug", "rotated": false, @@ -4707,33 +4623,12 @@ "h": 22 }, "frame": { - "x": 330, - "y": 127, + "x": 166, + "y": 288, "w": 22, "h": 22 } }, - { - "filename": "sitrus_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 5, - "w": 20, - "h": 22 - }, - "frame": { - "x": 310, - "y": 154, - "w": 20, - "h": 22 - } - }, { "filename": "tm_dark", "rotated": false, @@ -4749,8 +4644,8 @@ "h": 22 }, "frame": { - "x": 330, - "y": 149, + "x": 166, + "y": 310, "w": 22, "h": 22 } @@ -4770,8 +4665,8 @@ "h": 22 }, "frame": { - "x": 352, - "y": 107, + "x": 166, + "y": 332, "w": 22, "h": 22 } @@ -4791,12 +4686,33 @@ "h": 22 }, "frame": { - "x": 374, - "y": 109, + "x": 166, + "y": 354, "w": 22, "h": 22 } }, + { + "filename": "sweet_apple", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 21 + }, + "frame": { + "x": 166, + "y": 376, + "w": 22, + "h": 21 + } + }, { "filename": "tm_fairy", "rotated": false, @@ -4812,8 +4728,8 @@ "h": 22 }, "frame": { - "x": 352, - "y": 129, + "x": 183, + "y": 172, "w": 22, "h": 22 } @@ -4833,14 +4749,14 @@ "h": 22 }, "frame": { - "x": 374, - "y": 131, + "x": 205, + "y": 172, "w": 22, "h": 22 } }, { - "filename": "syrupy_apple", + "filename": "metronome", "rotated": false, "trimmed": true, "sourceSize": { @@ -4848,16 +4764,16 @@ "h": 32 }, "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 21 + "x": 7, + "y": 5, + "w": 17, + "h": 22 }, "frame": { - "x": 352, - "y": 151, - "w": 22, - "h": 21 + "x": 227, + "y": 172, + "w": 17, + "h": 22 } }, { @@ -4875,8 +4791,8 @@ "h": 22 }, "frame": { - "x": 374, - "y": 153, + "x": 244, + "y": 171, "w": 22, "h": 22 } @@ -4896,54 +4812,12 @@ "h": 22 }, "frame": { - "x": 310, - "y": 176, + "x": 266, + "y": 171, "w": 22, "h": 22 } }, - { - "filename": "gb", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 20, - "h": 20 - }, - "frame": { - "x": 332, - "y": 171, - "w": 20, - "h": 20 - } - }, - { - "filename": "tart_apple", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 21 - }, - "frame": { - "x": 352, - "y": 172, - "w": 22, - "h": 21 - } - }, { "filename": "tm_ghost", "rotated": false, @@ -4959,54 +4833,12 @@ "h": 22 }, "frame": { - "x": 374, - "y": 175, + "x": 288, + "y": 171, "w": 22, "h": 22 } }, - { - "filename": "big_mushroom", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 19, - "h": 19 - }, - "frame": { - "x": 294, - "y": 204, - "w": 19, - "h": 19 - } - }, - { - "filename": "lum_berry", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 7, - "w": 20, - "h": 19 - }, - "frame": { - "x": 293, - "y": 223, - "w": 20, - "h": 19 - } - }, { "filename": "tm_grass", "rotated": false, @@ -5022,8 +4854,8 @@ "h": 22 }, "frame": { - "x": 313, - "y": 198, + "x": 185, + "y": 194, "w": 22, "h": 22 } @@ -5043,33 +4875,12 @@ "h": 22 }, "frame": { - "x": 313, - "y": 220, + "x": 207, + "y": 194, "w": 22, "h": 22 } }, - { - "filename": "hyper_potion", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 5, - "w": 17, - "h": 23 - }, - "frame": { - "x": 335, - "y": 191, - "w": 17, - "h": 23 - } - }, { "filename": "tm_ice", "rotated": false, @@ -5085,8 +4896,8 @@ "h": 22 }, "frame": { - "x": 352, - "y": 193, + "x": 188, + "y": 216, "w": 22, "h": 22 } @@ -5106,33 +4917,12 @@ "h": 22 }, "frame": { - "x": 374, - "y": 197, + "x": 188, + "y": 238, "w": 22, "h": 22 } }, - { - "filename": "potion", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 5, - "w": 17, - "h": 23 - }, - "frame": { - "x": 335, - "y": 214, - "w": 17, - "h": 23 - } - }, { "filename": "tm_psychic", "rotated": false, @@ -5148,8 +4938,8 @@ "h": 22 }, "frame": { - "x": 352, - "y": 215, + "x": 188, + "y": 260, "w": 22, "h": 22 } @@ -5169,54 +4959,12 @@ "h": 22 }, "frame": { - "x": 374, - "y": 219, + "x": 188, + "y": 282, "w": 22, "h": 22 } }, - { - "filename": "tera_orb", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 6, - "w": 22, - "h": 20 - }, - "frame": { - "x": 335, - "y": 237, - "w": 22, - "h": 20 - } - }, - { - "filename": "lucky_egg", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 6, - "w": 17, - "h": 20 - }, - "frame": { - "x": 357, - "y": 237, - "w": 17, - "h": 20 - } - }, { "filename": "tm_steel", "rotated": false, @@ -5232,33 +4980,12 @@ "h": 22 }, "frame": { - "x": 374, - "y": 241, + "x": 188, + "y": 304, "w": 22, "h": 22 } }, - { - "filename": "candy", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 11, - "w": 18, - "h": 18 - }, - "frame": { - "x": 165, - "y": 228, - "w": 18, - "h": 18 - } - }, { "filename": "tm_water", "rotated": false, @@ -5274,8 +5001,8 @@ "h": 22 }, "frame": { - "x": 183, - "y": 231, + "x": 188, + "y": 326, "w": 22, "h": 22 } @@ -5295,33 +5022,12 @@ "h": 22 }, "frame": { - "x": 205, - "y": 233, + "x": 188, + "y": 348, "w": 22, "h": 22 } }, - { - "filename": "upgrade", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 22, - "h": 19 - }, - "frame": { - "x": 227, - "y": 236, - "w": 22, - "h": 19 - } - }, { "filename": "x_accuracy", "rotated": false, @@ -5337,12 +5043,33 @@ "h": 22 }, "frame": { - "x": 249, - "y": 236, + "x": 188, + "y": 370, "w": 22, "h": 22 } }, + { + "filename": "sitrus_berry", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 5, + "w": 20, + "h": 22 + }, + "frame": { + "x": 210, + "y": 216, + "w": 20, + "h": 22 + } + }, { "filename": "x_attack", "rotated": false, @@ -5358,8 +5085,8 @@ "h": 22 }, "frame": { - "x": 271, - "y": 241, + "x": 210, + "y": 238, "w": 22, "h": 22 } @@ -5379,33 +5106,12 @@ "h": 22 }, "frame": { - "x": 293, - "y": 242, + "x": 210, + "y": 260, "w": 22, "h": 22 } }, - { - "filename": "magnet", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 6, - "w": 20, - "h": 20 - }, - "frame": { - "x": 315, - "y": 242, - "w": 20, - "h": 20 - } - }, { "filename": "x_sp_atk", "rotated": false, @@ -5421,8 +5127,8 @@ "h": 22 }, "frame": { - "x": 149, - "y": 246, + "x": 210, + "y": 282, "w": 22, "h": 22 } @@ -5442,8 +5148,8 @@ "h": 22 }, "frame": { - "x": 151, - "y": 268, + "x": 210, + "y": 304, "w": 22, "h": 22 } @@ -5463,12 +5169,96 @@ "h": 22 }, "frame": { - "x": 151, - "y": 290, + "x": 210, + "y": 326, "w": 22, "h": 22 } }, + { + "filename": "syrupy_apple", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 21 + }, + "frame": { + "x": 210, + "y": 348, + "w": 22, + "h": 21 + } + }, + { + "filename": "tart_apple", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 21 + }, + "frame": { + "x": 210, + "y": 369, + "w": 22, + "h": 21 + } + }, + { + "filename": "soothe_bell", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 5, + "w": 17, + "h": 22 + }, + "frame": { + "x": 229, + "y": 194, + "w": 17, + "h": 22 + } + }, + { + "filename": "dusk_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 21, + "h": 21 + }, + "frame": { + "x": 246, + "y": 193, + "w": 21, + "h": 21 + } + }, { "filename": "poison_barb", "rotated": false, @@ -5484,8 +5274,8 @@ "h": 21 }, "frame": { - "x": 152, - "y": 312, + "x": 267, + "y": 193, "w": 21, "h": 21 } @@ -5505,12 +5295,117 @@ "h": 21 }, "frame": { - "x": 152, - "y": 333, + "x": 288, + "y": 193, "w": 21, "h": 21 } }, + { + "filename": "dawn_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 20, + "h": 21 + }, + "frame": { + "x": 230, + "y": 216, + "w": 20, + "h": 21 + } + }, + { + "filename": "tera_orb", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 6, + "w": 22, + "h": 20 + }, + "frame": { + "x": 250, + "y": 214, + "w": 22, + "h": 20 + } + }, + { + "filename": "upgrade", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 22, + "h": 19 + }, + "frame": { + "x": 272, + "y": 214, + "w": 22, + "h": 19 + } + }, + { + "filename": "quick_claw", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 19, + "h": 21 + }, + "frame": { + "x": 232, + "y": 237, + "w": 19, + "h": 21 + } + }, + { + "filename": "spell_tag", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 6, + "w": 19, + "h": 21 + }, + "frame": { + "x": 232, + "y": 258, + "w": 19, + "h": 21 + } + }, { "filename": "zoom_lens", "rotated": false, @@ -5526,35 +5421,14 @@ "h": 21 }, "frame": { - "x": 152, - "y": 354, + "x": 232, + "y": 279, "w": 21, "h": 21 } }, { - "filename": "mystery_egg", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 18 - }, - "frame": { - "x": 149, - "y": 228, - "w": 16, - "h": 18 - } - }, - { - "filename": "metal_alloy", + "filename": "gb", "rotated": false, "trimmed": true, "sourceSize": { @@ -5563,19 +5437,19 @@ }, "spriteSourceSize": { "x": 6, - "y": 7, - "w": 21, - "h": 19 + "y": 6, + "w": 20, + "h": 20 }, "frame": { - "x": 335, - "y": 257, - "w": 21, - "h": 19 + "x": 232, + "y": 300, + "w": 20, + "h": 20 } }, { - "filename": "oval_stone", + "filename": "magnet", "rotated": false, "trimmed": true, "sourceSize": { @@ -5583,16 +5457,16 @@ "h": 32 }, "spriteSourceSize": { - "x": 7, - "y": 7, - "w": 18, - "h": 19 + "x": 6, + "y": 6, + "w": 20, + "h": 20 }, "frame": { - "x": 356, - "y": 257, - "w": 18, - "h": 19 + "x": 232, + "y": 320, + "w": 20, + "h": 20 } }, { @@ -5610,75 +5484,12 @@ "h": 20 }, "frame": { - "x": 315, - "y": 262, + "x": 232, + "y": 340, "w": 20, "h": 20 } }, - { - "filename": "sharp_meteorite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 8, - "w": 21, - "h": 18 - }, - "frame": { - "x": 374, - "y": 263, - "w": 21, - "h": 18 - } - }, - { - "filename": "unremarkable_teacup", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 5, - "y": 7, - "w": 21, - "h": 18 - }, - "frame": { - "x": 335, - "y": 276, - "w": 21, - "h": 18 - } - }, - { - "filename": "dark_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 7, - "w": 18, - "h": 18 - }, - "frame": { - "x": 356, - "y": 276, - "w": 18, - "h": 18 - } - }, { "filename": "pb", "rotated": false, @@ -5694,161 +5505,14 @@ "h": 20 }, "frame": { - "x": 374, - "y": 281, + "x": 232, + "y": 360, "w": 20, "h": 20 } }, { - "filename": "full_heal", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 9, - "y": 4, - "w": 15, - "h": 23 - }, - "frame": { - "x": 173, - "y": 282, - "w": 15, - "h": 23 - } - }, - { - "filename": "super_potion", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 5, - "w": 17, - "h": 23 - }, - "frame": { - "x": 173, - "y": 305, - "w": 17, - "h": 23 - } - }, - { - "filename": "metronome", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 5, - "w": 17, - "h": 22 - }, - "frame": { - "x": 173, - "y": 328, - "w": 17, - "h": 22 - } - }, - { - "filename": "soothe_bell", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 5, - "w": 17, - "h": 22 - }, - "frame": { - "x": 173, - "y": 350, - "w": 17, - "h": 22 - } - }, - { - "filename": "light_stone", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 7, - "w": 18, - "h": 18 - }, - "frame": { - "x": 173, - "y": 264, - "w": 18, - "h": 18 - } - }, - { - "filename": "relic_gold", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 9, - "y": 11, - "w": 15, - "h": 11 - }, - "frame": { - "x": 171, - "y": 253, - "w": 15, - "h": 11 - } - }, - { - "filename": "leftovers", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 5, - "w": 15, - "h": 22 - }, - "frame": { - "x": 188, - "y": 282, - "w": 15, - "h": 22 - } - }, - { - "filename": "hard_stone", + "filename": "metal_alloy", "rotated": false, "trimmed": true, "sourceSize": { @@ -5857,15 +5521,15 @@ }, "spriteSourceSize": { "x": 6, - "y": 6, - "w": 19, - "h": 20 + "y": 7, + "w": 21, + "h": 19 }, "frame": { - "x": 190, - "y": 304, - "w": 19, - "h": 20 + "x": 232, + "y": 380, + "w": 21, + "h": 19 } }, { @@ -5883,8 +5547,8 @@ "h": 20 }, "frame": { - "x": 190, - "y": 324, + "x": 251, + "y": 234, "w": 20, "h": 20 } @@ -5904,14 +5568,14 @@ "h": 20 }, "frame": { - "x": 190, - "y": 344, + "x": 251, + "y": 254, "w": 20, "h": 20 } }, { - "filename": "miracle_seed", + "filename": "candy_jar", "rotated": false, "trimmed": true, "sourceSize": { @@ -5920,15 +5584,57 @@ }, "spriteSourceSize": { "x": 6, - "y": 7, + "y": 6, "w": 19, - "h": 19 + "h": 20 }, "frame": { - "x": 191, - "y": 263, + "x": 294, + "y": 214, "w": 19, - "h": 19 + "h": 20 + } + }, + { + "filename": "hard_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 6, + "w": 19, + "h": 20 + }, + "frame": { + "x": 253, + "y": 274, + "w": 19, + "h": 20 + } + }, + { + "filename": "everstone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 8, + "w": 20, + "h": 17 + }, + "frame": { + "x": 253, + "y": 294, + "w": 20, + "h": 17 } }, { @@ -5946,54 +5652,12 @@ "h": 20 }, "frame": { - "x": 210, - "y": 255, + "x": 252, + "y": 311, "w": 20, "h": 20 } }, - { - "filename": "razor_fang", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 7, - "y": 6, - "w": 18, - "h": 20 - }, - "frame": { - "x": 230, - "y": 255, - "w": 18, - "h": 20 - } - }, - { - "filename": "razor_claw", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 6, - "y": 7, - "w": 20, - "h": 19 - }, - "frame": { - "x": 248, - "y": 258, - "w": 20, - "h": 19 - } - }, { "filename": "strange_ball", "rotated": false, @@ -6009,8 +5673,8 @@ "h": 20 }, "frame": { - "x": 268, - "y": 263, + "x": 252, + "y": 331, "w": 20, "h": 20 } @@ -6030,12 +5694,138 @@ "h": 20 }, "frame": { - "x": 288, - "y": 264, + "x": 252, + "y": 351, "w": 20, "h": 20 } }, + { + "filename": "miracle_seed", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 7, + "w": 19, + "h": 19 + }, + "frame": { + "x": 253, + "y": 371, + "w": 19, + "h": 19 + } + }, + { + "filename": "masterpiece_teacup", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 21, + "h": 18 + }, + "frame": { + "x": 339, + "y": 147, + "w": 21, + "h": 18 + } + }, + { + "filename": "golden_egg", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 6, + "w": 17, + "h": 20 + }, + "frame": { + "x": 360, + "y": 147, + "w": 17, + "h": 20 + } + }, + { + "filename": "sharp_meteorite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 8, + "w": 21, + "h": 18 + }, + "frame": { + "x": 377, + "y": 160, + "w": 21, + "h": 18 + } + }, + { + "filename": "unremarkable_teacup", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 5, + "y": 7, + "w": 21, + "h": 18 + }, + "frame": { + "x": 272, + "y": 233, + "w": 21, + "h": 18 + } + }, + { + "filename": "razor_claw", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 6, + "y": 7, + "w": 20, + "h": 19 + }, + "frame": { + "x": 271, + "y": 251, + "w": 20, + "h": 19 + } + }, { "filename": "wl_ability_urge", "rotated": false, @@ -6051,8 +5841,8 @@ "h": 18 }, "frame": { - "x": 190, - "y": 364, + "x": 293, + "y": 234, "w": 20, "h": 18 } @@ -6072,14 +5862,14 @@ "h": 18 }, "frame": { - "x": 210, - "y": 275, + "x": 291, + "y": 252, "w": 20, "h": 18 } }, { - "filename": "charizardite_x", + "filename": "razor_fang", "rotated": false, "trimmed": true, "sourceSize": { @@ -6087,16 +5877,16 @@ "h": 32 }, "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 + "x": 7, + "y": 6, + "w": 18, + "h": 20 }, "frame": { - "x": 230, - "y": 275, - "w": 16, - "h": 16 + "x": 272, + "y": 270, + "w": 18, + "h": 20 } }, { @@ -6114,12 +5904,33 @@ "h": 18 }, "frame": { - "x": 246, - "y": 277, + "x": 290, + "y": 270, "w": 20, "h": 18 } }, + { + "filename": "lucky_egg", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 6, + "w": 17, + "h": 20 + }, + "frame": { + "x": 273, + "y": 290, + "w": 17, + "h": 20 + } + }, { "filename": "wl_burn_heal", "rotated": false, @@ -6135,8 +5946,8 @@ "h": 18 }, "frame": { - "x": 266, - "y": 283, + "x": 290, + "y": 288, "w": 20, "h": 18 } @@ -6156,12 +5967,54 @@ "h": 18 }, "frame": { - "x": 286, - "y": 284, + "x": 290, + "y": 306, "w": 20, "h": 18 } }, + { + "filename": "oval_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 7, + "w": 18, + "h": 19 + }, + "frame": { + "x": 272, + "y": 311, + "w": 18, + "h": 19 + } + }, + { + "filename": "candy", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 11, + "w": 18, + "h": 18 + }, + "frame": { + "x": 272, + "y": 330, + "w": 18, + "h": 18 + } + }, { "filename": "wl_custom_thief", "rotated": false, @@ -6177,12 +6030,33 @@ "h": 18 }, "frame": { - "x": 209, - "y": 293, + "x": 290, + "y": 324, "w": 20, "h": 18 } }, + { + "filename": "dark_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 7, + "w": 18, + "h": 18 + }, + "frame": { + "x": 272, + "y": 348, + "w": 18, + "h": 18 + } + }, { "filename": "wl_elixir", "rotated": false, @@ -6198,12 +6072,33 @@ "h": 18 }, "frame": { - "x": 210, - "y": 311, + "x": 290, + "y": 342, "w": 20, "h": 18 } }, + { + "filename": "light_stone", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 7, + "w": 18, + "h": 18 + }, + "frame": { + "x": 272, + "y": 366, + "w": 18, + "h": 18 + } + }, { "filename": "wl_ether", "rotated": false, @@ -6219,8 +6114,8 @@ "h": 18 }, "frame": { - "x": 210, - "y": 329, + "x": 290, + "y": 360, "w": 20, "h": 18 } @@ -6240,8 +6135,8 @@ "h": 18 }, "frame": { - "x": 210, - "y": 347, + "x": 290, + "y": 378, "w": 20, "h": 18 } @@ -6261,33 +6156,12 @@ "h": 18 }, "frame": { - "x": 210, - "y": 365, + "x": 311, + "y": 252, "w": 20, "h": 18 } }, - { - "filename": "candy_overlay", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 12, - "w": 16, - "h": 15 - }, - "frame": { - "x": 230, - "y": 291, - "w": 16, - "h": 15 - } - }, { "filename": "wl_guard_spec", "rotated": false, @@ -6303,33 +6177,12 @@ "h": 18 }, "frame": { - "x": 246, - "y": 295, + "x": 310, + "y": 270, "w": 20, "h": 18 } }, - { - "filename": "charizardite_y", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 230, - "y": 306, - "w": 16, - "h": 16 - } - }, { "filename": "wl_hyper_potion", "rotated": false, @@ -6345,8 +6198,8 @@ "h": 18 }, "frame": { - "x": 230, - "y": 322, + "x": 310, + "y": 288, "w": 20, "h": 18 } @@ -6366,8 +6219,8 @@ "h": 18 }, "frame": { - "x": 230, - "y": 340, + "x": 310, + "y": 306, "w": 20, "h": 18 } @@ -6387,8 +6240,8 @@ "h": 18 }, "frame": { - "x": 230, - "y": 358, + "x": 310, + "y": 324, "w": 20, "h": 18 } @@ -6408,8 +6261,8 @@ "h": 18 }, "frame": { - "x": 266, - "y": 301, + "x": 310, + "y": 342, "w": 20, "h": 18 } @@ -6429,33 +6282,12 @@ "h": 18 }, "frame": { - "x": 286, - "y": 302, + "x": 310, + "y": 360, "w": 20, "h": 18 } }, - { - "filename": "diancite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 250, - "y": 313, - "w": 16, - "h": 16 - } - }, { "filename": "wl_max_ether", "rotated": false, @@ -6471,8 +6303,8 @@ "h": 18 }, "frame": { - "x": 250, - "y": 329, + "x": 310, + "y": 378, "w": 20, "h": 18 } @@ -6492,8 +6324,8 @@ "h": 18 }, "frame": { - "x": 250, - "y": 347, + "x": 309, + "y": 193, "w": 20, "h": 18 } @@ -6513,8 +6345,8 @@ "h": 18 }, "frame": { - "x": 250, - "y": 365, + "x": 313, + "y": 211, "w": 20, "h": 18 } @@ -6534,33 +6366,12 @@ "h": 18 }, "frame": { - "x": 230, - "y": 376, + "x": 313, + "y": 229, "w": 20, "h": 18 } }, - { - "filename": "galladite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 270, - "y": 319, - "w": 16, - "h": 16 - } - }, { "filename": "wl_potion", "rotated": false, @@ -6576,33 +6387,12 @@ "h": 18 }, "frame": { - "x": 286, - "y": 320, + "x": 309, + "y": 149, "w": 20, "h": 18 } }, - { - "filename": "garchompite", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 8, - "y": 8, - "w": 16, - "h": 16 - }, - "frame": { - "x": 270, - "y": 335, - "w": 16, - "h": 16 - } - }, { "filename": "wl_reset_urge", "rotated": false, @@ -6618,8 +6408,8 @@ "h": 18 }, "frame": { - "x": 270, - "y": 351, + "x": 310, + "y": 167, "w": 20, "h": 18 } @@ -6639,8 +6429,8 @@ "h": 18 }, "frame": { - "x": 270, - "y": 369, + "x": 330, + "y": 165, "w": 20, "h": 18 } @@ -6660,12 +6450,264 @@ "h": 18 }, "frame": { - "x": 165, - "y": 375, + "x": 350, + "y": 167, "w": 20, "h": 18 } }, + { + "filename": "relic_band", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 7, + "y": 9, + "w": 17, + "h": 16 + }, + "frame": { + "x": 333, + "y": 183, + "w": 17, + "h": 16 + } + }, + { + "filename": "audinite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 350, + "y": 185, + "w": 16, + "h": 16 + } + }, + { + "filename": "banettite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 333, + "y": 199, + "w": 16, + "h": 16 + } + }, + { + "filename": "beedrillite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 333, + "y": 215, + "w": 16, + "h": 16 + } + }, + { + "filename": "blastoisinite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 333, + "y": 231, + "w": 16, + "h": 16 + } + }, + { + "filename": "blazikenite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 349, + "y": 201, + "w": 16, + "h": 16 + } + }, + { + "filename": "cameruptite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 349, + "y": 217, + "w": 16, + "h": 16 + } + }, + { + "filename": "charizardite_x", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 349, + "y": 233, + "w": 16, + "h": 16 + } + }, + { + "filename": "charizardite_y", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 331, + "y": 247, + "w": 16, + "h": 16 + } + }, + { + "filename": "diancite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 347, + "y": 249, + "w": 16, + "h": 16 + } + }, + { + "filename": "galladite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 331, + "y": 263, + "w": 16, + "h": 16 + } + }, + { + "filename": "garchompite", + "rotated": false, + "trimmed": true, + "sourceSize": { + "w": 32, + "h": 32 + }, + "spriteSourceSize": { + "x": 8, + "y": 8, + "w": 16, + "h": 16 + }, + "frame": { + "x": 330, + "y": 279, + "w": 16, + "h": 16 + } + }, { "filename": "gardevoirite", "rotated": false, @@ -6681,8 +6723,8 @@ "h": 16 }, "frame": { - "x": 290, - "y": 338, + "x": 330, + "y": 295, "w": 16, "h": 16 } @@ -6702,8 +6744,8 @@ "h": 16 }, "frame": { - "x": 290, - "y": 354, + "x": 330, + "y": 311, "w": 16, "h": 16 } @@ -6723,8 +6765,8 @@ "h": 16 }, "frame": { - "x": 290, - "y": 370, + "x": 330, + "y": 327, "w": 16, "h": 16 } @@ -6744,8 +6786,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 284, + "x": 330, + "y": 343, "w": 16, "h": 16 } @@ -6765,8 +6807,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 300, + "x": 330, + "y": 359, "w": 16, "h": 16 } @@ -6786,8 +6828,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 316, + "x": 330, + "y": 375, "w": 16, "h": 16 } @@ -6807,8 +6849,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 332, + "x": 347, + "y": 265, "w": 16, "h": 16 } @@ -6828,8 +6870,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 348, + "x": 346, + "y": 281, "w": 16, "h": 16 } @@ -6849,8 +6891,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 364, + "x": 346, + "y": 297, "w": 16, "h": 16 } @@ -6870,8 +6912,8 @@ "h": 16 }, "frame": { - "x": 306, - "y": 380, + "x": 346, + "y": 313, "w": 16, "h": 16 } @@ -6891,8 +6933,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 294, + "x": 346, + "y": 329, "w": 16, "h": 16 } @@ -6912,8 +6954,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 294, + "x": 346, + "y": 345, "w": 16, "h": 16 } @@ -6933,8 +6975,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 310, + "x": 346, + "y": 361, "w": 16, "h": 16 } @@ -6954,8 +6996,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 294, + "x": 346, + "y": 377, "w": 16, "h": 16 } @@ -6975,8 +7017,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 326, + "x": 366, + "y": 185, "w": 16, "h": 16 } @@ -6996,8 +7038,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 310, + "x": 365, + "y": 201, "w": 16, "h": 16 } @@ -7017,8 +7059,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 342, + "x": 365, + "y": 217, "w": 16, "h": 16 } @@ -7038,8 +7080,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 326, + "x": 365, + "y": 233, "w": 16, "h": 16 } @@ -7059,8 +7101,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 310, + "x": 363, + "y": 249, "w": 16, "h": 16 } @@ -7080,8 +7122,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 358, + "x": 363, + "y": 265, "w": 16, "h": 16 } @@ -7101,8 +7143,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 342, + "x": 362, + "y": 281, "w": 16, "h": 16 } @@ -7122,8 +7164,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 326, + "x": 362, + "y": 297, "w": 16, "h": 16 } @@ -7143,8 +7185,8 @@ "h": 16 }, "frame": { - "x": 322, - "y": 374, + "x": 362, + "y": 313, "w": 16, "h": 16 } @@ -7164,8 +7206,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 358, + "x": 362, + "y": 329, "w": 16, "h": 16 } @@ -7185,8 +7227,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 342, + "x": 362, + "y": 345, "w": 16, "h": 16 } @@ -7206,8 +7248,8 @@ "h": 16 }, "frame": { - "x": 338, - "y": 374, + "x": 362, + "y": 361, "w": 16, "h": 16 } @@ -7227,8 +7269,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 358, + "x": 362, + "y": 377, "w": 16, "h": 16 } @@ -7248,8 +7290,8 @@ "h": 16 }, "frame": { - "x": 354, - "y": 374, + "x": 382, + "y": 178, "w": 16, "h": 16 } @@ -7269,8 +7311,8 @@ "h": 16 }, "frame": { - "x": 370, - "y": 301, + "x": 382, + "y": 194, "w": 16, "h": 16 } @@ -7290,8 +7332,8 @@ "h": 16 }, "frame": { - "x": 370, - "y": 317, + "x": 381, + "y": 210, "w": 16, "h": 16 } @@ -7311,8 +7353,8 @@ "h": 16 }, "frame": { - "x": 370, - "y": 333, + "x": 381, + "y": 226, "w": 16, "h": 16 } @@ -7332,8 +7374,8 @@ "h": 16 }, "frame": { - "x": 370, - "y": 349, + "x": 381, + "y": 242, "w": 16, "h": 16 } @@ -7353,32 +7395,11 @@ "h": 16 }, "frame": { - "x": 370, - "y": 365, + "x": 379, + "y": 258, "w": 16, "h": 16 } - }, - { - "filename": "prism_scale", - "rotated": false, - "trimmed": true, - "sourceSize": { - "w": 32, - "h": 32 - }, - "spriteSourceSize": { - "x": 9, - "y": 8, - "w": 15, - "h": 15 - }, - "frame": { - "x": 370, - "y": 381, - "w": 15, - "h": 15 - } } ] } @@ -7386,6 +7407,6 @@ "meta": { "app": "https://www.codeandweb.com/texturepacker", "version": "3.0", - "smartupdate": "$TexturePacker:SmartUpdate:e6d832697add1029764f6145e5fa98b7:47250d3d95167f73038d290f7a73b96e:110e074689c9edd2c54833ce2e4d9270$" + "smartupdate": "$TexturePacker:SmartUpdate:5676fc2ef4e2b6e18c96ca3c80e7521d:a6286201546cef975121cad6b35c7005:110e074689c9edd2c54833ce2e4d9270$" } } diff --git a/public/images/items.png b/public/images/items.png index 7ddd284fac7dbb81a9734e37a5316daca79876d2..9af295e16ad5205282e3d7fb3feb1486a3a6c1f2 100644 GIT binary patch literal 51675 zcmX_m2Q*yY7w+iY=yi-yB18|8!C-U}(R**vqW8`yQG!7P(S=0x-bIfdJzDhMjox{F z|F_<|>z;e}+3ViB_C4#IwfA?vFG^Keo(P`~9{>OlDJsaQ0|02q{~9jFljpNc$zK2f z1E8v;DXV1b^5o%QW%u(^6E^knsh(Y5AMoCq&`4pVyr`JX z@FiPug^sXMwV&QcX%~G*-PeV^a%^)QX)G{PH`gyX`rRPV{3Gx3?VIBKy4#M9Znu`Z z?6~;_lVCMZzYlaD!XrZGZnpl_xaIZz{2cPT)wi>~HCl=%c{WZXLwfagOd?h3*Xg*# z=i8;$cR%y79`0KQKFj^c*S=4L-u(*rZEW)GEUbC*BCxL3A}xP&ap=4ZT>p~4=HzQD zmrHlo{e2(l>G1GO>DiK&iil!J*FyjB?DwA|D1@rgQl#7cZCY*4YH3**AN!A(jIzso z7g4+K-0sgt>ws%R7uicx=W>Nep(J9HrLZMb2~E`9-7q&c*_sT zQ&!548)kQik$qd2es}CuzqGpL`*pj`$^P4Yi*|?9XFDm9{a%q2d)w=O0F7Vu_qX&+ zF_Cjx99JC~-k(n3)^8m6`91f3bPkxCe|D|&K-{lr<|G;{Aj_uWuQs!V^#|^BJS3^P z{I5Qb1~*6^XKGS2L(`TYn|-f!s?`Hh-oN4^0;yAr<5AaGEOogmzSAGsNcnuN0%qq` zzwu^$L}b6`^L+E+BUFV`Y+k< zg-;6r&s|+v1MoEIpN>1u%!I|c|D4VWdTsy!(Coj4_EVz3765<%6lEkez329S;rUa% zue;1X)O>!*n)$sSKP-5MM1cnzx7)P60y74)lj{AKXZXy1JUL@<%otN#c8tVeoibd~ z_?&MaW#wmkurOUrL7%@Cvqa+uHAKgGxnmz%FZzrKk7#H;otc;(hbMs#&)*dkzHvG) zT@v0BKIf8@d~CZ{5vp(IA1#wR90h+C8`;4SxY1QJ(3Qtl}Qsmsy z_rk)PPj07JIs=8AtS2(Y#j9M%IEcxca@ZUb$KspORhQZ#(8; zFiclBt9xO=%syLu#t?V1c#K6{RB~TB;a#QC54?tEw|&+wQ*t88zwe%5RC+}hyM0n@Fy zZE415ttV! zjWxM~7>Y*lXOW#NOKTz17dcN{H9?_(go#P_!YE~;dn4VJ1rz@4rx>YueW8iY9nXf> zNCp$#!TSKz)t~q4$LWL5zQ=6rbYR*5BF29C{zV=prx)*HJoSv^6G&uQGc)p1vzPGu;?pK zP!mc;Nv7!e1Y54+;Vxe-cCkb_62q49s$f4JH(w55XsWBHrM<3B^1KfWbbQTcsUFnZ z^_j9@N8FW_lJM&t_qoD|N>ae=Y-J??U3Jpo&*4x1(P}TxL*U1`tJa*;KLe*T6^XYU z@rvj7&sN?IeAwJd31#|Re0{BP+o$qrHtEol*Ra9sC?Y_@Bst3%m2Vx_D=@%)r1)Im z(v+B-bd1`jW>7;sn_if3fYu#1&ue0XcS?|!G4#7onIwgWhllf0(uBM1=+~kb43R1u z9jhJTq%2H8!X2AP>5YyFSdXQTQk$VGEi1ZbqoC7fUjlA-Krcfh%_|bc`>u)I@W&|^ zP)7wq;lXp=DVzN^zB?GL9n)v>K=WcjxJKY(?8Eo(^le9XziwKv2;T77LlSorciG;X zh})odVly|U1=S*}c+rVHG(lmJKY#ul{nggAqw^YJB1N0(hmSu#aoNKycmY9rk_Mc% z-xR@y0a20*>2|{_N4vJ~Y-5`o)6#SUnA(4qA9W>65{r0QspbXVedYd!dWQ`xi-$&T z;R82uI875~t6)4PJlv9?6h$zLd|Y>C+sNDmfisNX_pD~@d_r55WDMCkyL`Ik#gt%F z>{*H~ox6QIkGEYMkGK5u7A193vR>MAN@acqV5Vas|qJ6n-c#uQ4%x|N5o?}q31LZLq=r3&hu97VdZuvWnkwAyCmuB08N3Ty2 zVkR*kON?Ani#g2YyljBM+U0-qyKi@gptE^bNJWF6eg6($cjZ`4HR^K#kX&Xxcg=1$ z$ezD(T;Th0x%-___wxEw9(6Ic!&0E3!T*C%cs038m~VE@x;?zFue2Y|I_nL_B5Ani zJ9dA3xI#^G+~+hOH5G?BzI*oWatX;F&~bDY(6*$4@bCI)aji2rc)W6ZL{En3YUS8% ze3yN+a0{A=@mBfh;+VhG!uR3@8+N_?yKSdKGi0Jj$qprbn4%^TcrQcJtvF_R40jh` zJLv~W^b5v|%zqfIacdGEHTz9{y^2Ng5h+u)hXzh-M{CmrgL-8!&FjS8BuLxsIQ{4n zLqS!ciC;N3$yMfcg6zfp$#TYsq8k1LY$1Af&Vz3M?VL8p| z(iX&zL~*|`NwmcCGMg&I(OXQU}*6NK(8T-ctbk& z-zD{>g4U=+EfvPsB!wT+Jc;#LnQ(u zH7i2$ip&Q>5{YgxTlcNJQR-Z5PxwW*p!c#w6GHL1+ z)7KYcR1uGv>Do&L$Q9<5nsUb?M-lfQyYcA}NN-nN06N{Cs~{S9Nh9R1+{B!>CaB$F zdo=gRvR*RW8T{SoL_Nrj*7k1mC4P4g#$pS#T%3i9>P32S9l?S;pKHkt{rfigNzYtS zdV^3848B_|h`~mHwUbmzIK1IhJ?m2RP37UY{dyS(>ZYXviVv6AD=kV8JVo)yMVbje zUzpVx@Di?y?7S;_tYxo{T5}vKT`|U9<$(d@8JJ(;u8-!pZ4KY6)%->b=h_C$Te*q# zOpuT3D z>ohFkKf}ofs)Kv=)Fbtw9W~UtlZ`lp?Ka;il;@qLOqB}iR^)1(S9v%(ShW5qFxjni z-#^^W;5WW;=ps^I>HcHxkM|P;MUX!Ek>F5KMFntr9fO^L4LO{uX6X;!dY--bHswVbk>TCo5$?WX&skv0%ikwbZsA1h_GN`t&IZkBBJtQ+3^f zt%}mn5BAfVXJ7@tPhW5_?OuoDj)c$IPSB7;tBP{WT=#0EBZeE!_v`7>An&%kGlFf( ziqXT>Sx|v+#)+EFanssDv1sX-V0)~u=kGkP1u{8nhV)G=Sye0 zYPg>P)(*KR3R3Kuz_FhR2=w%`o22TqhA8981$;8P1Znozw;sG#j3d`Sj2cK1jM+c( zgMV|>CU*HiYx@&$MR*8+RQ-qCXh8Tt}4)m_bX@{jX zZm)Yb8`MWIMei6w?tab3>V=1Ml0?$isO#dsp*5LiH@c;fDMaN;hkDKbtJx%Q*M6r| zhU7~yS5wkClRSWP8-{soL|R*8#OKCAZ6sv8dcXMzOz%Ey?Kcx!c&Ti`>y+9I9y?i=MF)1&5Sg*tNjXhhG%zB<4fkl=+JrJ;#qnIsa<^Fj;1( z`CetUgL%33`BXG#{i732v%&V7W8?LhwX9J#B`3ZPAf|~jU|iQMbL`Fxz8fpKVakDoHZY5&$W64 z+_V!pm*}D)X}aCjvRxU|w6(BSXT~PodFvJ>LGMcXwSRn{YCK0l$30A&nb0zQ4Zw=>%l{$L zieo`aYG#91Cq1Rs=qtte^4YVEFae2I+u~-vZ`-Xm&%`UHGGgKRz~x|Uv)q4+KwLL- zXDzOu{Y){Ho6Kk_Q4~W)f5zMW`DU~9eQwaA0^hbi`1Uu=1SStPo|qD6$R;D(v#by< zeDcg(Tw-Ek%*@Ok1Z}BY1XGoEkteG-#4rNr$*D>PG}vmxWeH-IvmCoKs%w zZ!yqS=LE#H(LLtU%DRBHw=B9dU~V!@d?fs;&G{&_mGH=gfagg-&+m9WOZE*3y+AAhH@zfU%oPx6(;~*pv?!6v^xkY zKe)WWU9V0%eSiK6>@WufMD5~0?^-PR9mb9g98vqBrL%noPzzKjS+m zqzmS^(}+?P;uXN{O908>qqG!?u??6S8QC=9X<$u$k!^F!uv8=-iq)Qbg6h67co6P( zT^+l21DNAuig$H{?wc|UBIMbCJn=gd*?~7ZJJI4ZcCI?OthLNS6KE0C&N6%g@j66> zrKP1sMVX>rbg*UEi5kQ8b0~0%8Hl->_mS?%)bvYl3il7lOXAtHl+=J!`&R-lscQTV zD*-El52wey42VgfJtZ)y*HxM^^ETjDel`zDm>SLstl$vx&D6s~Zjwg(L~xYm!oB~j z5+4~Itw{<8^xCnlpyY5t_&^Ba0iX3Hbsp{#eg|x0)|&q#NqjJL^(*&=%QiEXU+dk= z3V4a2`LRifH(W;dz|3sbpNY!m1yGJ_G{bw+8grH3HGhBY8>ITCMIa10oXv~FdY=sc zRvYIHAySni4m%Zb*2fJC$};==_b=h^WA~^py}L@vGCic-Tu^r~x;*7vd{Nv4D=6l% zT9gaNN7rB^&iMYVDA13Vki$NXXqHe8=nifYCj?*4uK~h#pdbVQnc>^`J!$Nt3uvtu zgO;taIM9%8@P1H~_c?gILigEvqcC9?_7o)`ayZYIMpvkz#4OmN#J3^(WmIHHSNgDv zw@`TuOXMGh5U2=Q9Fy-b=cz&^Ubj7={>>ta85_x@jJO!&{TeQ-H~V<4{T?0g>aEoY zi5!geX|(Vn!g1CP?M#X3p`(xx7|lvBRbO8MHpyq4-8@Fx69{PLFvpLHga_#O_nGNX zqOs%$3I$C~OMMpzFg7GYX9Eq|ZbXF0*BL20(I6ZgQBlL}O!e$i2&@*2%z368mYac9 zl%oI*?l@eyzE1mC({?{4vpR&a8o^f#)9(#M$LYiHj$xE=&RMtg0HK`ohok{JT+X;) zW@FTFD^9FEwYfYV+E?Xzv&jSH&4eaj580v+3^JocoFCf8f1GtD>^h8?@Nsvg-2*C; z$XQA3zLCe14=H!8CVMvN_nsQcI8qcGjoa2ATo( zOFY>WY{>iDFQ3DSKqG)&1(eR(*zRxYcbkjR&fR>njQ2N+f|$tpH)~G2sgs~?U1FLy zZy=Gu+K_W@e$P^?crzyC-=S60lg?3taD+n4l(1!UJK{s0r^10D4@rmgG|rD!X3arC zP4MIk>rEjRKbglnH*)#oZKo)?z}73R3x`UB)k^n5K&MZILDNXH>}!~i#*rBa2fFEZ z$ltadBt8s{8xhBNskF%t_OT=!f4U)b2fatAI>4ZP0jbua`d z2hG8%3Ti{k4_v;wIX)N0=r{XYeRC|lhO?Vl0jUkKOtH-Y-m7zLHd_u}^G0qZ9ibyb zKjhFx)>*~&hl<56zA@BF9i~|woj4g9QflWP<>>0zCY6K^^$5GB8W3bkXlifDc;RI5f*|EfcAH<} zkAS^o?`|rpo;NVErjhgr__9fe^RfuBcZ1Od=F`n4EdB;`MXPcg>Pv}`!=6en!-%(u zmSPVE5FeH&`xBkyoV|EW4UK1L(%M9f<>iO1{Y;K~LjdJV3#~q(TLDQZ$wxvg-3s2N zYioUC3RByOUTgoj5=B0=j5bFC=d)UH#`w&WmzFhX-C?#;xvKr{_Ia0Cu1Kqq@808> zkERwSRkXpE z7xs-r8lqqkH3qWGlV_w5bky?JRO!v(X8=u|?e3aw7NF@+;^Ocg{`inK-OVJUj)jhv zX_`$>8mE%c_Z-ralX}9nMoYEEx}Ei)x|@I&#lvfcQ03a-bl0{~_Y`{E{leM&2@P|$ ze#yAe)uVO29CAzLg^g7H)wlyw_W)I`ZJ}kZ#n-!mg+p-Y`+BMo$%6#^(NYyz3IlKq zC)pD~K+L9~t6NmWbsglBT_nTkRdCQtAcTx2LQb%Slyr9`L?Mp*)OK?(V;O$Zp|T>~ zVlA22cCxc#q-++w{lZSoKS3x}fb%JP9v;qfnz9q$5j_gsxCD#C>103PbWBJNl)A;emix zDXHt7pOJ%-$e{ zjq5D9$PgJ7DQ{c{;Z)9?gIdvSOibZgo%qkdL97DasDpppaZ9REO_}f4gI@*r^nrSo zd2k%-awkzqH2#V1zo?L@zQ2aS^T zl1$9Ix{kHx57lz+=GBtPsHRBN=+ld1Zg?(rOn+&CJ$o5VMX#QpY16XwlSE|7$A_?( z27L?`BMH%Oepd*^@*R-)c1e1>913i`I|&UAZ4RAZaCK|eE0+t8`84+FfPW1WiD?}G zg$8aN#E=3*_~Tpt_WAa*9Jkf!#FH;nI~t%J4+6!Vzad;ekqs^s#qSu_5)+|u`S~us zekdj*M!fo(d4Q~ijB(KsQTtc zc@IvW!ygv|*Z`+qGMr_y+d4g7pU5hsMRBL8V^OE_UMt2N({l`l%)jU7>303;>`~Sq z41pgUR5*vurwtx`w_|8kB<=;{SpOtj32r-2A=0I1uC&wJf*y6=tHiXTLjjSZ+m}{< zGQGQ9!If-4fYgEHbFkzvwB#Rcbf_7-**Q0Zv6%1TF`wJK@%76OQ!Wb6yf(%7a%CYU zpUEhx5m+!v@e@Wh>Fv=aPc|^-x^jSA=;UN|sp!`H0tw^dp-JJ&jKz)mmu8h!!f4Eh=Z6$YgpDpbNsrJk4 zv#=IJjeub_Ii%QSx&t%R?=tC9ao?U7lqJ3(lNNo{-a@c>XT1BPtp!qa2J>*$jgxXyO2ab#T zh;l5FWsYHxH1Jr@n`G&Hk4Bss!8g2SZ)+PtweV$qaN$rzLY6Ei-f`jQmp~7%n18s8 zPN&1-PV{K3!I>WQt$xW4RoM`_e7ATLK;6L(nJbYXx}bU0I(fQB)LTF-AT||tiwA_( z*$dlsxuDv^h?yMznV;tuV1{`}5zn8shY6aSD=^|(7EBJm7jzo9IhWT)BQ66Tmh8iZ zJ=yQw2FIkM8V^+z>Ee$zH;p;|{qnm!`hyzN2U||UJA>KN3A_`6VnPZz5K5J_X=YZb8EDHd$kE}m!u?lCg^^0VV+8VMimiq zQX!&egl6gkAC>V1$#DLyaS3w7zwNCr?#L^k&iFD-Kd!yW-;wB3nVR}k_Pd4yh)tAY z1oqWtBVeN@W`@9ypFGA;wDqTY zf6W&p=W!l@e3@kyMS>2)W{K}08S%RaD<7}!!VHhlGC9tZ!()XIx0EG(`OWH8yQl(- zd6yAk$(;6hjYfd1c5F7*{nm-`fsKE;z>fT;iY>zsOXBpR~(J;V^~ zz5-$dP#}j{P9RO(@pxmS;UUviQk~{fC`%xMoy>fIjor~s3FL?jWhZ-1ot%J^m+OO$ zyN7Rr?!yNlTm5x9{8#J`LUOx|3tFHYi)8v2CAhj~v081e1SaXn>y>{2R0J{4dOQjn z3Ev%7Gk{!Jt@!L)R@Wsx}M z6t|K5Pb6bZ?YsJ88X-Gt7%nEfJO0(`d+=TqPME7TSfR^?!0OHMJkdL8KZCH?@tPAg z34_xWt_*K$j8y<(c0jD44Cb*noYF5j4%FbjGk$#DQr3rcG9*yD59zZ!6mU(C4-b>{ z#99IQz!j)VNg#ZbRh+n6eHcs~o*R&mQ$?zkj{hyYm^MRg*)X}4B>xfS+@ z);frqg$N+kj@ik(5&fPq+dS=4K{a+_J+9<9$D<5i6fsCGe@M3uZgsdm&Z6O1_bwnbq){*=>R6f#$zNb-5@= z?qSnycifSC1#nG!{Cf#`qGVV{a-%d2Ub8yRotxNw@$woojU%4c7{1;d-0=tdw z%?0NaIx#q+VpdJ(k{0`PLqCql}Lj~SdnWG7KVxwkS~YOmi9B#nsgU7lOJ`jMnD zKnQT@{ou6At=KOd zBY=)7@-GrQVdDssy$nW&s)BsaOxo=3eIL(#ZmTcsqevZySbV;50AY)Yl}w7JXYI?R zd$B|vZ>P@STe*AE8>IJ9X`{6Mx<)4yH6yJLL#{7h0!wdUm};qd3?k z$tl(g%4lI8V)^MCVZCyuIPD!t=)|b@G_3+W<;)CuJXZ1SNvJg=qW9!qwZ>bEk%c>4 zUF=5sZ^}wsIEz*FZxV;rSH29bGbyc*j_X8kIraxst}E~@t6kPQ)CK$2i21=vo39G* zsOMaVT>L=CsiE+uIp^S<<@B@t{yBX2W=GPZ_%}HewDm!NJ z=)e(^%B|GqC(`v(KV7ZO*w0ihl$N?i{HbpA#5{NHF_egHZ!P(C;P0TMBm8SeK~g3f zHET)`Ak6zG^(WZOE={E35nQEMb8Os0*+-N;|HHJfvYVl)@Pe_J@{whdyTQGhy#YX4 zb297N&mRngom~67_{9~%Xx5DWoT)V8y8h-e&0Qvec_!%jWQcPILxFsXQ(RccaaT!{A3QyPe!g=pTvoyqFJ_91Daxj|(b2PM zGdEKyw8IEYqGvdw9aZXsL(*EV`&)(p7anzGDcSM^{MWU0fTUt2ReIkJWSOgNL<+C=7?}!$f{}yH}mCbABQs z_{7aA;H`^8R}(*ql{MELT7*)~>|W`lSb>LAR3+brLycx{u3Q$yyzcWQPHt9kp1%tMR1OF7V=vl~F_MjbB zL4`i!h!k_xXax3`7v!t4eNID*ZF|Gx5*V46kYG5t)`?syf@+|p%eqd zp>jWa!oa^tdRmcJSw`|%MR!r+@pO!oRaWyKb2`o|&BJ$Up+t}LmYca-f^21Mc(^2H$$eupGh!?!rr3>K%F+|fwa$?CΞ-O3I)TW0kwEt}#8M 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 VUQ#{dA}#KLV1+=j7I%sk_ZA86TA)~q6$+(T zDG;Ra64t42aZM+5)>NHo-+J_7)-Q2%uToCnU` zPlo^i00*G2ZKSI0^6G)Z!@(^qB*enPa({oXuC9N0eD***JVC+lpit=T?c&PD=E2pC zzJZ~&O~{YkeJu@*tE-!#p~2DV9~sZ(M<-`(Us%6QNV>i1|JMF@8?&)~f_aynasR_J zts8UOP%%-htEi%K$-`5>e0(>mjX5^|edIH>_2>F@%Oehj`CD_g^S*Utu_uGCtVH|f z{?GiywSP#+;L$%-X~~QAUeuSpZ%dYU=rg0jipw9n5zcfq$&tC27qOvXd*f8q(814p-8gk#%h+``XXNhm?)x3aHCzBS*!#J|NW$3X zmETu+m4YO?fe!I!DCLbv(EU}~=!9=T@py!W`au7`-0adysJCA-&vcIb#eVzT4Fn4$mbRx{#gQDUbH8&z#ty}JRs~=MOojte{*2) z^i5;c(B)0|`_UM61MjNq6(bL?CdY*-qb74@-^w`abdHb*?#NEx+X7Bg(sG(5ZQ!@cAOI6>4L&bjCp*5!P1zXei3q3|QHk~ppvfIO(2w_)dQ`%drMtMRS zsN(ESj&dcR?3eUU@H8qLOB%&C;sk>w+?XBSxtoHdnSSX3V)XFmoRQ>pC3NOyZ}??; z%_lII7}wQGvwPN;6{1F=^H!>SPGRab7O|}AYWPGBX{lo7Oht0ZwAKAHb#3fI`gtCS zv89I#K;-jG*AVc3N`Ln_RiZ$b;(<%(rEcyG0Fc4|>sS>E#=a}~S0}3D_NT4dq4bMa;jkAj=ydfQ~^ zXXXpp#lJXKU+#0HjvGQfYf4K$X?TZ(xmSYqWkxoA``FpovP&qwS5l%C$xlWcZV2St z&ol~S`nCKtb-)mSy_{h6!o z|5hYC(${zzdOn#Li+v~*M9!Noa}o~;{?z%#2jC3-oS+%=i7-4tqh zapgAenLq}nGCxV!m=g_mS5cl6y_g-THdy z<0HbDJ9WMa-ppsugAZ5Id0I^9_&GVtI$FIWm?ZJry_apGszl8w(2_xaiMg1vW7apD z7!dH1-pf#WTxfjWr3)*-uC?IjV;t1@)J^sx7Ah~y${T|ADlGc&p-b9pquRygx!VOf z5f`N8aTA>un&;GRi})^mWsVO4A4_*L^;mOm{3NRef%y=qk>*)!Nvt`PV1ar2eow4+h)jPv24t35D(Hu8D0XxWhBxs%A?0`f;@J$)@enMRV~GA- zP6B&^ZudK!`=Hc}Q4>3Y2dWTd)&QSbFR$5x6B6}8@Vuq7)^$h|3m zA5L49Sv(JM|0=4Yx%kJmwes zkUJ7bQ1K6n!@Zf*z_`b`&VYo+0!&YQyb)M>$S{fUXHUvL*dmGa?ic6Qi%$w$ur{23PBDIXjfa#=w~An|)TwijZzw|

{shFohoxN( zq-X>Oy$17wNLVa*%&eez{pX1?{*K?;;q?_B*$eYVFX*YM@kBlNdrnn*KWJt6&`I%v zz@+&J07AG8NKNHoW&V;dC-L?kjdu^=6(TgH-hU*XT3toP$5|+b=!d~s^|V{`^rCq> zyh4#lV%)>Z_<}Wtf*nB6*G^vYdlec0c$jrMi+DT#Q|>;5>AxkyZKWE^rlhV2{Rr9G z4C`s5i=N;+Q!A^oS#D# zJVay7F`){!PKKI%G>ec?;LF1(hJ|GepPl_Ytgif6iY}7CigJgd4P<))yG5OL+M^(d?LTT63fInG1=8cX>nejD$JuUMkPl6zrqWC3v&Ha9 zo`0RhCm)VDD6qm;c>_5vPmIr@ls{Q8#R7_As^@=%iUm$5{fNLR5B`!Uhg(ukGSpHP zS!IX!6#!FG(&)vw>A=n#LIT~5932z+M7|g!ubs#8g+JKDA3ZTcS#&6ozoEE){iNf7 zPJ&ddH+mCWk~iV{TJ7K<3(*_TZ95Td=PSU11s0@v1y)qaSqeSfek*u%7cjY%Eno?a zQ#e6Qx#i5}$YKA^^FY)>m zsrJfeG`d1gZK(`}QQ4uCWQWy(x2K^|+gMU=^A}V!!!+w5hhitD4z3+VE}J}ut8d%u zgT&%+y-K-nhy=+#;_F2NC8v09Jbvfi+)kz9Gp}h#Ch^|5iuZ&w2UO|xT4Ryoz^3YF z%#w$y1v`_|(vqS4A|`L|n(@EU6snu0|Dq0tI2D0So*T?}PGFDOcv2xKKXFvKV@wxX zRwlIjpY&mop*i8H^bxNul2`zCgdYsI*N$EZyu(9R)YU2E3X`_fiAE*2N)RzYAtnrTyftnTr2PppZX#h#+vi4Tq=b zllGem=h! zQD2a#P!hcO$WK00a%ed8p>z+5y<~Or%$pL5;8L9MvOfiw(2Jp(i!KuMP4J-IkKHT& zv1M*z#}RMTLnFEWv8}Yao4JQP#oKUbv3@!}-tSrxl_EYLM&W+u_))ypt(2tF`l(&R zzPCQs28HbcHs0mHAPK#=ldf)(LB+BGfH)4Xr9~j4%t2givO3#;C)-P6&F-_pw~s3xiPh-f=%7>_UW!BxSq-7JA`1Fe zzq6_um_P_v6qu_`@(Yq)>N zmQqnbT6(g?+f2b zA_YB-QIDCyKRZFxksMD265uM)vu`v*fAc*}Tyl|(|5V}BO3D{S(PleHB!e2fx%Dk{ zBj^6#oA3We{~w3@)~C>o&M(l%aYgR;tocViUfTsR1J&&OHfk|g7PN|GxY#4LiZ5|o z%Oib4nJd~d29`1$uvGR`Gig1q;unlzuZ|yTMlf67v>}UtMJD3)o=9XyK)Xp!$of4M zB+(}~vWQu#4Q7}KyLxunw{50|p2|;p1!LL8Y#8g7=LQtc9KnuhqVEk5`_xMl@jDWZ z->{f{w}EM&6*AQ;xa0W73T>yqX$-vj&|&xt0qbHXULo6DYhdomGHAP(y9q;yxh$iL z8!IYWKUFk1IvN@2q%6}$76aJOxW5XVHvF&t>_~L$Z&AaJ7%W+d5_R+bdb}vH=1rEK zQVB$y$RrOu7XsXbAD;N@I2h?TI2brknK|f)9i-J9q*-6GIQ|3lZ)X@Vp{u&QUXdFwsJ8Wz+?^6dCNY&Xn0*5+J_ zXZzZs-K+Nx#S-p)Eo;8imdz~FTP}Y7mykPnBa7M1rtw&Ub!R)ZS$f8LcPPaq(e@cO z{97`x^gd|pEtWVJEH*;+v+U_WL;6B>jVN|@RS|Zqbls=@aPjcuZoHzsP)z+h7_<-_ zAr--H7M=1s!cvhVRo3h~?yj2iNTk#TIe$!q@J56#7G+|fvGG~b=zUH<_c{?YdB|M` zWJ$|GVpj$rtCPC!jM%lo72P~N$QZm=oM9(-217<{0g&NWyQp_SQ8Uc~s%7(r&JM~M zW2bYAW$(vL^_VSY>yX}8>QierSSxW%Wqfu43$i8)-Jv&CRTsmhEMD~Rmw0q6NeOLF zp!VQCz0=*FB0w|kBt_(Q8`@U9u>wA&xK&|yxCo#&1hhQ39zWi?sI~56kRvCb96u`NWqDYk9 zBl5UUK1$#wLYU_IB1fh>)tB|-owiXcM_5?o#q|N0j$v?j{cbS@=5A7LQwV(oascg} z96L$x%_%;jVF|nJfRakp6Vss7g(N(&3o~U{JwN;rcsZRPKp~14!Y4-UiN|j2F{4?MUwa=JdP%OBpoaOiheCLl%DX20seP82lnr@)-ec zHW8A7K=c7u=Kbr<6w~r^w;Cyl;(kOvM5|tX#081N7M;c4y2Lv%R!4^CcRYUl7~~+t zI!(0w4wR(gNP*_(_klzXdNo&V9{$wehupW^@ZiJEwCqnYOD@pJO)8P!U1o6`hhgsZ z-}WO&RZL^Bw$HyZIz#iK*+~!$ohG%2AZEv0RX=eXcxuKY=%cwuKn4!Tk8(4j(&kV| z3{e0=)Ccm|yH^u!IEe=a{}7^$>d%UP0jEHh8M7u_3=~&sYHIjG*xl!#eDaHvt?aM? zlI|klOYyhst`myn$K5wq^3(*)cdMyc&?pMfn`mqmTX;lod&byvQlUk31QgPM(6n3R zN5&B1yqk>x!O4j~3hr5{BZ-kOG?*Yw9EQm)*fDa!!VkVgOb&L8S~M0vTFY1|tor9O z(YJ{&0agGpdk-OpXB=PPz~z$nOJ}%WZE#&;I{g}hfM6$nJZ+=bzXDyqXIJz@_7nHb6PNnhDP%U zsnBaL#AZ$s; z0BnqNh!>VjB4xCPBp9OZy(2Wln1P-)$r<<&I7Zm!9{CLi)W9pMzJO@+TOvZF8RT4o zqZJTQy=Au0;BuCUt6~at>|hfg=Qe^E`HOgi;_ya9O)kakVodVa^Yqg*5)_X8XuecS zp>9Kzko`6Wq2j9hG58L*2dE~1)9v-aZrj@Jiy?E19#XSR5Ia5GXX=->Xp|&(q&K+1 zWBa5O;L*}*6(uC_I9lRI^sDXb5$K3Uue$>wLMd-=ok^CeeyM5L>IV7<_>Few@+2@> zxrhTX*uXpDUKtzj{?6v)wcUaGOCVk}9t(jo2BPTPiXLgJ8F~P(oBL8m^NU8QZMOmY=qhkIaxAcrUxwv zl%*~WkL8d2&fY+=W9lkKxOxNHr^|HIal)9vx-Xot$TCJq6(5GgdV|jlVU0YFGf^!1 zY9=-NLWtNGvp_r&o8E8pS>gC_ec_gX({}T2pWRAowB!&d`?O86KNqC#52oA79c?K=%FtuXuXbsmzeRt=Ro(aq=>aV!fD_H$& zSdnlvJRDxz50USzP+yB7hV&d`ZgjYl)JD+k2cp zN;U>5s>mv72OC&lZ5w|BJmz8Ocy}5S{|e-zcW;pW3`^?CaX$8&9}o-2G**yzSotEf zu5hEBqW81EAa~|hmJXhg#=$(S5^FUNX;eU7^zYw+xIg)S95M{O#zHzYynOFKD-dVg z9Kje}N+{~}j02=UB%fq^Y8wgfenL=;yM;$Zd&1WbV7N1HCyeIe*VaL@_}CrFO^4*I z=E9`fxkBPD=ZQY$Xnx)9$ZZ;!32@d9&_)I7*NSWNq7`0*-2TI};U>PlxjP*k;s@yi zbozsva$46Bg#A|0N6Q`?{Snj2ho=YW`^L6BQ-09l(cy)#;6*#m8c zRaERZ_*(SEYn2rn*wWt2`)x_@@E6`*8Z(N5Vp>cOmNs+wx!Qw?v|}cJ7m6LdBc%_A z`n|-Q1kN2C5D+Bv=ssTU6ug1t=C7=9uDSv?F*nD|u?m_6>N(=7{n6AK(As2LDCXiZ z*vWHG<=d3BAigmmo_d@X`FY2yDQ^L!_hyhwqrcX@cOGs!^c1&X@MV8-Dl*ksvWei! zWd3Pud8VaUt`tf5{gMX%UCbKRa6&BFs@X>m{*$F@>u?iR_r%}OhS3<}=XC5O)Bf1! zS)OS!E3pg;5FNcvNElX5j@#^)Gnez@nCBiz8T&LmeQ{@|NMNz(gZPJrp!>j=m59^& zCSiu$t~0+O0$|Dr8&^y5Vgv2nbneVHbbi&9&?R8eMrvc`B==d4fToIyRKm>6v#!0H zu3A)V$#buZu+}DO{XaE|WG#`{u*3V!rqcBAm-vR?IGgM0a?Q75!XhhW^Yr@DFEHWx z@`YVXA38h76SDD!T$q&r+}&Rs{YQ>@8V)I`2Os`5wdzKzVy=jlzq40zPKmfWNDV(QR}z6B|BbH6H>x;+jZ7}%E2A^^{v6RGm`4sTBf1m{^CJ)`-W+` z({KKlJvW$cJj*e)w*vSsA&!0}lpyBVO%XVNg!ekv23NAF-ouHTIA&9Y2XlMlITV9& zf6+?7|9DV#7gN9$KA20FRWs%q7Qc>swi+bB*#tJvZ2Gfg=e#=lSI^t|)K<3yE(CK> zQelCB#kC_(1Cm*TM3I;u%DEK`8qV2#EC0%foZS?xJY67Qrrp?rZUC;HqKVReef?`W&-8?T3W&DpqPLwEt zXCRGEvyp7FTc!fN;}`Y}c;Ds95>#RvGWFF(XNqG<=)q4qDuLPFzMUHwtjJf+vY%>R zTSvg4GcxcE55uv4##$N^Z%;eZejT*ElId{#ZH8uTH6@@*8rA(*f}f+O$&a)z5OB0$ZED z2UXQs{1m6IGN*s#%&XqKd7~0zf#T0SYm!QF{v*$rAx0m zRaoi7V6}BL%ylvwA{&m3=HQGm%j=PBRs`ePrC_ro2A_n2=CQbKGk6HKE!tw07!kIX zE&WB^XG*dKb7Qt6gFi<43jTp)40qKEC0%P*N$;&ZBh`DR7P#$};024`Fj0`;@e_w9#`l{*aw;zNs5EBrcNT!B+PsTWQkA zxIAf)yt~>SeycS~^^E}dZ3R3^9;l zxZjqaI1z!yzc2^$i@fIt8rVAyIhvFd*v0~eY!O(Z1Vf)m{_a<&z{GBnjO`?}TeOjB z05GwrgM6fX;H321$+6=4dOWb=HYyR=sOV0P62=*1#zjGJU?b#zO<2g4SshJf$KaXb ziuD1Ys0a@toU3P`?X7Q2wL@1TFD)gq)k;JGgPucYJQU)9A?;EjN^DH7RN=#MIo_0H zG|K)Pq_GoLqElpjZHdCI zZ#Fq6qdj4jdo~h4-&rpmE<9{v$sb)4R*KuZWry3&x=PCF@TD*l1%7FvOyAj`cnFa#G7c z_KU&HOl>rlHUM~OX6xah@#=KT|I8k)C}6B32COF_CaymEoA!>-l$iJ*4CKcMu~0yA zr&qw=^G4!%%&D2`<>OMtlru*TO5ix?|JH}AH)5i{H*2x8WJF>Tp)4^8t~l8W*spow z)(LQI+bhJqYFFA{eSy?2_n8r@zG9Mn$cB8F>6Zje3v$vym)3;}d>@nvq56@OeHdY2 zm74Ljshmp4$6;firJo#ju7|hnn$uTp`ftZT)(0sbH)uH2u=I|;UrqJn@)0@jCHh5# zu<|WhkqQ!w;tLHmrXAGFA`+ zmNsvcOyypkpO;U`K5p9MH8(J*P9pki@`1$Y7w6JL@WSP>B=r~%*C_^s0j9~6jXgrOk#zg`A`{E~jE$BY3(QT-dAYiE zi=7sozd{5-nR|0Se(_qK#-`tn#D*!F|I^Ib*70i>&L)r{PT&eAhax!3eDZ%`%k z2{F7XiH+4&Fado{52CD6w~Fn*@K~TQ3rE70sYeeGPi+m(G23rn*gORbi*r4)!L7IF zzs`1I-3$;CSMxUj(~rH!`ACp576uz+cTuwz?t*sta%sHlJ)5^d~eut#htIFQc6j*VhDj;Y3 zG+=iEuFxdPiauGsR?cSjKW7hwZSC0~wbT3uxGT&5(zNpZutiAkRJ~I@POdc28x@y_cLIVfVtipsr zn{^Y~%uLT$g6{!Wl)hxozjBdY(vM@|En&tqTfRMv8J=AWsnSP>nA=yAN1hx-!Iwuh zNGz5R`C`_7MA`XOT+CSq;58?)QjWG^tr~)u2|#>c%0bsEH0>Wc{J~a1cc*sfYPuGfFB^r zlqHMhP76v^*9ty2-T=Jqe#+_6D^BH6?!w#KD;I<-aZr=(tNYwnx+nWhD}SEeU5=!I zwYq-7+n$x%HQuzC2<+p51)hp!*4{_{jlwKZaWV=&v2UB9wwO6OZt~DUj;NG^`+@Y+ zs~@F4(JUzU)j6wwuj!?DELk6P(rrO?vzR+|XWHU%Nx_x%+}%$y<;-_c*4TN8(*UpibV+y3VIpjD%_ zHDO5dItmk&8F9y|z z$xYWKVYiGL3pI4t02ifeXF*Rm9#h90l(=iPUiDKje>=LpwL#onZS{FLH_kNj>>oW?UJ`!_5I{2+A=22x3-ZB zN|HZFTC90dlR1}|QD$I+n&tvrL1c#BO4x*SBm!RcFP-jW5P_blI#(FeRS+dd>(IUY z)=#FemQpUZfAF+Mp2z@2=i9R#5?V}QoR?4g@kv4zif9)}VaiVS{tDjU=gu~p3J=3i5eO) z6!t&)SvrhDZA`D^Y0!A7ORb0JUn6j2pGRu9c5oQWHivcbCxVmOc0u#Ka5LVMjW$V; zhz4c@$yE>{tUzTZ%cFtAX!MmS@71VAlu%POPhx?BHkYdH1cJZ=t=C(D;3LcBh`g@@;j+t;Z^ToSyPlojv|0k+~Pbq@6V2?Z`< zE4cs40`RrNd)3PNby9A6EqO+gtsLD+aw%(4+l#iNJYXjq+G{VTPf@@f2;q(o!NMt3 z5*C5`94V0nLo|ajZSnk{u~2-|`VgElQDHf9C zp}+f|O8T}B7aQy*znq9ve)8>V1;J&rm&LGR63S`!1z>`$n`f zX%wp4s>U?vbAbr;w{K2^K2MgY{%b*MxQ&&jL?Q75C$To^eNrlddGdfjFFPOpsl1nc z1gZq?@ik+L1n%FV>2Nt30GuC-fs-gQg7jC>xzkBCJ1TSEalUYyBz@DTla~7~@%KF0 z0qp`@J6rS(_-Zl5_Ymv#-r92PX5YZ@;s*s~kR&ShLsXu;8+H4sH)i0J;H1K)C za{5OOuV(}isVhE4ak4;I0kw+7r#zS=lrb$pEKQqnXkkQ*iHv0in$D~(412WrDA8OM z2znG-00u=nX?+@sp6^&Dj+dW15`)3|4r+{PuPvK1GaFDm1|v zVpT;8k+r8fqm>#An%Q98Cb>HyVRx3?+<;~a3<1OUA#HQXCgH{tH?4nH!o?CO-0i=5rVJdfZyd( zKcWMk#wtlfDoJ1=J#dj8cRyD?L6i9wB;Ey+$^A{XyZbV63gZV1y@AjIjpAhhz}QBl zxec_{Eo0?y_F4%P6Ol7l;XBnegE2qWyR^EHzA#wG{5s+GPtn#tbYQw@$}9hT{n{HV zH`pD?$Y8{mB!M`cH`L2B`y|Q%QX86nEST1!vI!xe`#m^T-BW3X#0bJP~C zXrTUXxL@4ecloBXQ^$zYbW%G(6>uR+7h@wBtHk|%?ePSiSlE@;&xT8@)wZt-4FyM9 zGNijsa@&4R4y>ekswRs>X+z;MG+^tAFj1MPS6flMAoapzAkI%wqFXAf@{g3e9U#dc zxiCRhsJ#mdk?@PE6=E~A=Qlkuti);G7G0<^m?&}MBlU6%U*xDFhk5U0OVs`7eG=2u zzIRu;$!@b8^d!HVu`h16|B|Pxd8xrpFrccd5Y+`@J}Q)@G0&BMGH|*pFw4$eRKE!T z`$|cvvk&h#acUvEBy|QC=F0I%*Wt%<8_5z1Na(X?&+-Gy8dAOxOpVn}_KDe<+B+=p zvi05-Wds1?Cd{#57~B#I++LJp4E0`r|eOYYf705|y3ryMomsluv{N z0n4=xQsv%$`zv0`MO!w$UB6;T*dd!z7t60lpG7ct|9k)^)|c&)R6YFU{TbqP9~&Bk z4rrrhxoy1QGuK@hKpeMS_xCl6o!=m`yPyH2xMm&l%2Hmo>2Bc7jQ;e@zF%)ARe=e( zE~rXTkz(;XMNBD;ua#s6PvrnP^x}w{|7qy&y#Zzdh$2$W3kMHaGBiX^3yXVIn}#sJ zzfO*MwEr!Z&Z(M%obCyaOn>80%AywouROu``gBht#K+n>OBwU#fM~f zJsRQox9_em81KFh7gf{uLsvP5!SDCXvHxCybA|wMAO+0x6N;VVN5@YToSGk0)jJOc~I30sl@9#Y1Gh84 zyr6q<+q?LWx3{;ypLg$?*H?l1SZzS>C-(R~89^p7rb0Xd0y$*-Mh>OT!^ZcH)hmi! zsPCnoc3fdke&dR`c9-Wj`YhQlPewOnFl9l%59H9%I4|jLC{hWd;8Fv{0v53m+_1#> zrEWQUXUvSj^&gJSjN{_Nj+?r^zP!A7|8@8bhSY2iYUUwuT> zC05E%>vtr-+k`>2ME#rDeVN@pm4V+X8UySp$V7Mf0!<2Uw&RKXGvBEyZk*_p^zvd% z5Ujs(-8_<~_57SvddEla{;5$U{j`UmN?0uC-G44WAy%T=E9--~GfNwxy)0qC;MCOQ zAxkG0n*s7UMKCAmxY1#JMo!Ez%M?fm1GZbaEIt(=;VH1~n5_WS6{C7m%;D-kjdFXH z<|&JC`$a4xDXep0&~!&aAM5H001Y0vf@qsgy#zZ9mxOVMj9%^aZ>PhzF`@*jC0ICe z^B12O>o?A*KvQAUTHAlCTl;%-`_)nuBwq zd7^erj}kdKFJ~kt+D+p$M>UvBH+L`bJsdz#@YcCvOwvc4=E_j7<|}*5D7KB_9w%6^ z653a5i35gHQ-iq{ZdSxDozqn3-}IamR1{S3!XV%8Do8xpi=Z|SCz3*MgPtS@HXsz> zE+uBdJm}~~0663LHJv{rJcP#?0qquj7eT|02eEpgU=HoA_y{uj4BMd1%m2G#gSq?5 zRX`F`ilT&=6UH!zmli7m57c>{3^6nxW-%5e zpnjVO$-Q)n_uvR<--xLa?6K7vp8K&T_Gi>`Iy2-)F8OeQy&yFmBV8VS*F=un3o(Iq zu>022@eQz*z`s$hg1^7Y&6E$ewc=O(-P74_XVnr7Yw9!D(uX~nMC!ZZt+TCBy`PtO zLHmp3Z-`yinQ;CcwjFY>+<|34%#eHJe~VdPJucb(qY>*%?&I;um%D*K`4UR=@t zdOdpky5yex9)wcH$nY?@5UBYEzO{z*5deR&QKhG7LHXsW-Zg}%hIKy+ZQ9dSFEQi_ zNX5eGpYh+)jqLT?P$p+fv;R__#*51A-BoGlPAIs4lppRmS?XvykstbG!rk}T*JM0E z$KzC{4ABG|8y{Zd63ABTFu1v} z9+6iFDS|hX%{8EFifn5;u8%?e8na}1S1-?>nOWMy!>R`ooZCKA-eQxTg?v5k7BRZa zD@}NSLXWxn87ZOd`$EXc0y4?Du_Y~=2{u$bk$Q=vshM!)?9nVW^+rV$^fo^Phkpna zF`ZdGqX?l9_xwQpd(_jEn zAuc?4mA17Aft_N%0+)r$g{&>U(y{r6wWh1j?$my}4cea@9Y$(^*A0XpH>m5%`;)%n z7LC!R5kgYaOzUm))LdU=YGTDNyRxZ9looF-I$w&F?0U;z0nPsI|F@|Wc>R3g{Cwf} zF2Rbg5;I>}@aP0|n4w!AfNDzoK?@NX*{)Jw(h`Z(UMV_cPnfmSdMnXsY;K-lrCunS z_%4&71fTSstba)2XG!R5sX0S7AssB+zj2ek!9!!x40_a|Q;!SSwd99a!}jzy%l}Fv zsiy@6beno42-rVvWv{N-(GxUa&sD^`IXV$cxehmtJ%$9lS=8wmDJDZFI}<=?sNl{E z3kwhd(I;Pa&RusgmeSK@nH11pt+A^a++@Tw(K-PEBMEbaT*3Mfk4q-3{>uCJuRJ5) zS&zT5f&OC6{G?P$=;QGW_C>pu~Th3w+AAGF$9d!+6s|T}zue>xf+fy2PF%9Kt|ulkvMCFPqBK;!n)Zzn77W(Y3p}$##=gexH5qHqd>I z%6*r+KkknwyDLpsUO^7`h*(es15wbj96ZV3QE@cQ9_eSl$%yFBmwVseA6n4bNP~)q zONGkxW;2CU|4jytFaRZ%4Gex?+-sd#7)^e5bmIXky zZe7~)!Pfs!+TY`At(lZPsO7wHHE({{BNnS0JzL^=-U{tY^Q3Zs0uUUE)FAj@r)NJM zU0okyIdQ7whE31^7%3b=|B&HE6i{`O3CKuEc(S{_OM3Y~Fd9RF_IrFBnd7AajNhN^ zwk=#G#CsVNIbB5~eHDZ66~;>Hmtx65XD5E%!M%?i$%uBQ!38R=@bG{7V8_)=5)&#P zqt(`gRa-!i)vqY}5NEGQlno3s#SXfP0(*J=mt+k$NROyvsbMN9Z++5fQMg?%AzAs| zPra4+6+&3t{Zrg0fM82y&tFRbumNBQR*UiB{dS zmtLD7|Hstl^A&AkA<+)>uZaq2j>fBpXc3y%aZ2=6yFf9gu&;L%f zb2CJ!1RHlc7@L9b@t>@8%boc^KI+D9j*h6S+X%-SXO6dcDkN#JZVNu7L9O|fkiOdu{Nh^d{ta0U*D%V$}nJ_dzC`y+Galk zEKawd4CGq$!?LF9qsd`evQDD7p6|4wFN-Zp0$cKsDju+2y`^?N+ocihLD7rNfyF?M zD_f<=84fCod$st^CCUp^UcEe6y7bkW7{Z)%$l?t32hIW*g1mo0?cpZ}eK^E&dA9wr zIEfe(D&WMxd244eiGCOkNHDGjL44T%Yx*|7mmDl%G@7NfB92hE=8Bq755tjUovQM_ zN_>qHcS0lY6#Oxi&`5FI`M$S-Ed?%Z%^}Z9XCNoBhy}j|0XH}`ZH_t;YLTVbZ+3Is zFbws6S4-^vW(U1>P)9fvYj+6U!UKWdSq_8;+$)T)5;X4dfTEP35G&6{f$k(By^u~q z96bRQI(;APc;o7!20%~R{j1yiHHnFpz~ofn^N*S(t>8LWXz8mF@0=L!e4^Cl(%BL< zE<9fAR;TF&x!}Ij5)0-@ivnE+7n+3hI5^>IpT=aupCA!N8vs#rG&O^&D&7^3kM3K! zi_G>C-pGzLyZO;M+ZLgV^Q$xNL^6e^;ACBqDeSjL0V;H@MM8+vjWv7{aA4pkXbjog zx{`yk?d(|ZND#zr*wzzV$ z!%l3E-RtuM%*`>S|4eFjJ>Kj5Ru(rXg71$x|CG!Y^<>I>NoNxqF$OhIhbpVQA`I{R z900a%zw3gWMbhrN+6A;Y7S3WRvc&h?`SQh5cxIBSbiw4*H+vub+v+fLhEfRq`t=Ai zShO$H%K~9{rJUIL z%|&vU)J<8DsE3Wh>&FE8c(c|EfBgQ^94IE1bxTmEh(TAJnEJ5-4|v;#4XFxD3Ccw2@vA|b^Z|h)B91i2Xu5|IR`ll`0k#L$ zo^~n?KbeK#vVUZo$P!;cjE-4J48qt^xJ>T9erdxCA*5}?PBlBw6|vxVfCYGcdOB6F zZ51|-vP46GZgh&z2B2OY+qZ(>L?;KvFA0jH?K9((O{wUoS^@6;PjU!f(0G>=t zGzsj7nrX|m^OcphkawMG@`6I=tvx*lV{By#!tW@yPDj|M6?)S4iRDAjjTIepiw-`vBfgur6p(km zBf{~Wh5wG#cIssupUOiZ>3c}Ydoe^42&^fdW2NsJ&VE`H#NR2fMFSkcXqNEj3ryaX z{oD3%76kN`gp!OwkI+VBD*r?0dk^h8K}Wf-lElbM{^|#3F(qZALL2_~fXj>pWqt7& zl5|!E7!17(yVnl{q{M_Gk;R*_wfuys<@;UN>_(ys@7-wpYhpaCe(75Xbe7#GHCiY!@If_$d3tj$F%Mgu#5VM-#Vt$v3Z<168qJ z@|y!awV2`-`s9$rJSC7_(;5BH$q9h%+mgXxQylFoeJs?HIrzaQ<+AFBMAP*R*a*F0 zqm*L=)te;DyoG$&t<*~JKcwrO8weJb3VwW#!x)HS*Vl)FY2n;_s7kx~6FSoXE`=ju zA>5#mx4s}Ru{$E9WbX*G+gl0X3n@V(rWV7y(rRq5;txMfZ4y9!LZ#gbt#dh-&shCm zIs9TbO*+b?UgvBrZjkucU(hO0n=_a==4t#2sJ#INxUA!P%l z^(bDQ=WH-MnUbJfi}3bx8@}fFtMc&h@aG6(g>><|_5|QH7ECRY7fS+)4H4v{i%Mb~ zJ;i^1v)89Ku)&JlW4csDDJDCVb%l(3yWaf8j^gU7qghbI?^SYxFps#{RF(d;{bEc| z<60wJCA9&6jC{IF(1F%B2gA_C`j3}!LUx-P$AgONy92#n?neQKXF~G)ynY0(KJ6_E z8n}fg&Kb4T=Hr?lMBRa3yGunBa*EYLS&8tYdM8`w(IzL4R$9*XLa0#4Bvw{?Y5?sI z&;H%7*4v9fnZiOqe}ws0`43SeT~GXf3wW*SuRn$DK~poj@d1N=Th3oJogL{8b*IQ|=WjlQgL`rCWV=MCU#J0NjC1)aE0iU*@F zD&++>KIOMd(iK8s=FV&WBAe?*RdNOMW6eVXJWB{E9)ZTcK3vRh#z`A1iJA31t6BbJ z8ZNfI$a`a}h>N2(-`18(?H5cUH5gX9{up2>?rvYryTIhTs29{_v=UjGnuW!>qa$8g zuC4=3KLgAr=&FX*NK&){_)Vz+1ORDcEf9bXR|88LT1XmZX7~R40Q`HTi}^)8HLx}l zF8KuT2g(F|JoJ=73EU2_<#cpVVZJw4cS#{C9xtH19dv^5& zTN;{ucPAYI8{BA{TLsS&x3js63lSx6yc$S!r1*9mMfAJegZ!xKc;dN?Ah5MXasNCU z31#|_I8t_wqay2f?3H}X~zsI7@c zhs@-0Qc@$JSQB!O?iNCWU0h93LS7o%?_;4^+Arw_|CgzAzwKDz{)7x-1w$3g(Z6ZP zOPsZ>GNV>dNH7qe-9Z3+cgD*KjE??Oigp0; z&jeg^FB8NtGxQ0Q)W+#CrIBwr#`4JOs}hZF!+9B)`s7Jlj@Y@qb47JHQMNzsLsHLD zabJqL`4>Bg$`?6m5DdO2VL2!v72b(0qZ|~9*}I>AloS5ne>gNy}ng{gJ;CA!1=ei4&f#^$$>psQ(&1<@l4nW4!g5LIlHY{O5J2Ydi4CKW&$2Z}G z`2C+p+mSUtu{AMaasR7P)4Q#{-u3BmG3_%Jn4%T4o4V(L=y>uPr1N%S@dABq z?a|tBYWI&t_Ge6sY(Fjecdk&5gnCHXZ@8%o>TB<>tTAiw8C@Bhk)$6yw)FiKwK3W1 z>y|$(qBjPQ-saf!#8IvD;$701e;aZ7p;qrN^7` zWRgw1P5Q3G+}CZmy^g)w6)-9Lf9AWV4cM(|nQGB*7T=d}t45pw-T_-qt!c#9_%6iC9sTft#O;jbc z;+@iFgqxtZS$3VeK*cD47Jr@6k*d~70w0mcAT~Do_6Af+?vb*jxdB{UvAg{DizU`N zZxC;g$8lWbSy7`%;rE*qCLw%fH0oh#PkdB|2-m=RAD4*Uu%%5|b5URvr7AthkpP`o z*!sT+q@+`nF~O1KcUQ&25|oA%!miG5%HSiCOXs_qOxcSR@HN%7$x;Iw$z&cP zsqF1&p4zMx-|0+~^mHH}5Dea5UQ`NMriZ-$Lao>CedlrRRzqZpCeed$vj>MNt41p; z-R@AmCdjB4p!uM7@4$_7UO|bsM!5Hzlut|En5>v@XOB7m6&)qt00VeM#VWp6DL$D! zoaM!NQYk>A=W+T@JwpmAu06P%8k93lG!Q3g*eOK<3}f_&qCNN@{&ULcL)wR$uO`q# zb7xIYnBV&+lB>ZE9K;$eCzG=K8$EO&28oMeMMcHxeD(ez9w82n;AevSn{m4d{c0PT zubmBSlev6Bgnk}}P>b3`Y?%-kOolh>6$E8@!uOK!INlWn>!M%pPdBTt0^L(}*armB z@o8GQBYpCw*SaLQ4ZEIc=wd}oR?9+1<|IkvC~FlYA+IyTdi&FR(!WOCZKbsQTC6y5 z^x=gk%94nypJZEj39t#Vk^zgZc^5wET!f>8hRVQt*s4Tu76nGqslf79?f0nZsqZT9 zbPnRevytc_lI)ghUv<3#d&0hv}icw%w3}2OvgTE zGC4!S;nau;^3XL0-@eX}Bw4&p9PS6w#TBPJ54)SuS)v&JFZ8c-RL6!Ac%b#yKo=%@ zuq4LDzlzHP^{fxr5)j^|z$D@M{Dkr#Mss9fY>UwBeWi%M9P6RMs8#X@STMKcP%sut z>~y9oTC~zVnRfm&*AGPGpN00kI|cW*!$scrl^TS@Q3U4yu0C<@FMiX$gYQge3gp2Y zF%<$3mmagxj;gFty=zS%IV$^HRe;Yrbsl6o=s8`N^V?aC2>JZO@v3CBvw+$M_G9w_ z?RD!zm(Mlg%{>byRb1o4;1If4EOa^Mmd_788y6LC^yP-0Y?`?vIrd8fo*sX+SpqE@ z$t0(~v3*8`iGqPd9eh&^6D&sP8QH1lQS;AwVG4IdwN9sd&;%V4K{13RhpM!{iD7xX>a2_zrcOJ~>nHdW$inY(Q z3-#Od#RH~{a)1b87O*rW3}5$JgulMgQqp^}ip-{-eJq(g$o;)0{4P0po=y$ENM=EJ(=FE2i2Um*8 zyTeEd#z$XFQw?y2X)XQ$di&cPG)AFvxDYF=kWjf%t)C9U&M<98n_i z8rqqbsVqr}#rj^q@3@Nmus9zPWBygx)GflP2iyVEfJRDH;)0YMXOVgq>YLKhfn-%S#T)|qW;PY3NOBB}!0U^d!)HeR|8d;78bs!DRn z^|nTf7crvHhbN*pL!nSiqP$C zCR|7N!t!fsg_9D`q+svQ8{j$XPze*{z)07+MFvxz&7J~{OKHSl#Z@LaiFkJto(`Tz zhQbTj7SocXm?#4`+EEp`6pJZmp@+HFti$pa;Jr>nZ4d^w*=sKm+SAy+L!#}A)pVVc zeG9BTl{f@KFi>x?H%2T_Gm_&30RF4>9S&rOD^ygJP671pPnR}L2ZRKdsg1T?DSrB+ zB97(to;@R6fR@c>;p44Afr_A+C|$zwYWGL1Y4KNvhMn7Zu{uj{oqPyy)$up!Y5Lhd z+RRYO$7{^YyUHX$DQHdCCA~@tVG7VCRWgPc4=8dG3;P+q8MpJE1m38St5Id%<0643 zE8Ko`28_qeVI-?IEXh5_(BX3xj7}h3);Zrr+g?$=-;p?owv>eRk3e=;-&AO?C`;OA zI6aWFIz3*{5;O%@p&b(nu9!*Z^fp$8iD2+V_EzIdK|g9To~q&$(*)rNm;yl5#Q+i> zu>Y+SL1Ln*kU+}0spw*>>#mwhd|=Sh`O3r<5;&FhZ26p=F(ep07%fjJ;JAxcRN!*w z*Ut+9nXWOjFQBj_s`9cX0$Hu`JR$m_q~5XjK$r+Vslm>33cygrJ z;Z6^%7vT9?gtTE_ApU?Ed6<)9Cm>ii^E|6O&4ybPNT;NJ&W*Q!VFF0vZ5+#_*_crw zI4^@{i+J&{O9yu*bzGrS{>&2)3pm^GLk5CEMAFY#?v2(|y|1j)D5{3cY}e{7gE;XM zct)Ol{*8FdzjMez>yME4#l&#Q9QXK;V&hD0P!&>r7!mk}kjwyIYe?z8YKWO{ZZK~PN7IUrBDtV+ic8z$fI&6y-u+pH6-Gb{^EqmCSahW1)BR>j?B`^QhNOc~)!He| zGHq#OEMyQ-xM ztV`|22+9R6hT9Ry$jfi$J8@))UAxx3Q@}!=wls0g@!Wy z(9UedPc&w^g1s#f46p5xL<3r@K9b~efgYuQ@NhSj$i!OS@Y5okH%Q}k3BB!+IQFYQ z9~K&&$;*+>txdr1obb#xheaGqB?4J+po_(D?k_V+gZ)a{W9I!513`xuTsY1K^YhXsyq1LQ;bnnrouNeE50d(P zgM(m8$KOV;L?7IS5LrNT+)D~Ed-nXgAH2$!A7krh#lfE~`}HP#6shGZd0zJjJ-nlA zg=Z_~(Iitju85oCgO2)e59MmI|gzr8uK`)UA1JQa7Q~Srt z?l~TCdLlft`?Rzam-0|FA=^~t32k>M=qcbO8{59<;vv!Eeuot=TZ6P~C&isFl=edy zj{=D~skkLW#$79(8)=R#T05vjz5UKS8L0>Ds_mk)Enr`B{PJ3GuKaeMCs)?7hvxyM zZo)#g6n6s%M7@99{~Z=pGWr%YD;kt3Sv3Do|4bF5&o6s=3edANIv(IIBpcEB#vO`e zkOqIoLm(wTdpCGOT9;#15S(iAHb;j<#aXGp={=z4EuS|!`ZEKz=)Y9BT@(X}w~lwI_tdvCw22i_A=erlnt!M; z>3sF}0-;i{_3Q61ploy>okCW#1>K!(!H1B~7&GR|Gs6qAAbAi{8a#h%5>1E*`gL;MAbG#>3zpQ^GCzo(n4R^1%4S>PWPI6|{w^}7lR z$a%%f?Xoi>4x|(f4ecV^1Cok_@&fsGn&JR-#N)wS{^E1aZ*evTIBNFbO+O6vZ+VjE z>$kTv)Ey88GKHPS(v&3$b57C17{PsW*@6N1;(@-%ozy82ilsT6`IySy% zgl^Ehcp7rfp-?s~arj$3ji7QvX7KP(U zggzXpv|uScG)6KIWixlhQgmSR%OKUO>!S(HYkm|>7sMIpvTXo3L>pxvKPg}o_1@39 zK@>I*Y9yqII4IazPZI^+;@{To%q$`FLo* z;Z=O4<7hz;k;KR)+SBL!+QU9p!Qmvy>$Pvb@dHg66DF|Qh{K%>=p7_e;Q6~ga>=kJ zNA-brJL&39B<8h$*doO5k$009lROh2?=5q=HhAB0}M|gbR*srx&`T|4cGQ1M>aVQD5C;+lhp=Xicu9>j&Ftr zpKmu|Ex!3ppUx5C)$W!wWohjGdJRsK`Xfs>bFtaJlfu*B@F}5NL;Z7=ygAB9X_D&Y zwv4FLORy@$(dP~Qj@C3twi&nX+H?|I$4P)G#%4bJ&AK1(bL-73fGZvmF+|Q_RDYJO zKUmn@X77=@>c$O9hqF=Wn}rqIu4ZMRFeXOd`La>ss#0PxmiV(CQ!` zU&7`)@O!{wPV7@HQlF;NRKAaN+*^JZjn|>6rwUztmtrIbcGJ4Al zSe5!sI=h;b^e2t_*V8Y{)zP_=m0t+hgx%>ldz&XA7t*n7X#5*QC{XhB(WDCPy`8=`8C=MhFmd@~vOHT=75=+C&n7#-AJD+P8;@8ncBcYVqR zc)m2yW4~togENTZEr|m5xot@@!U@bL8AO`j{gtJmR(ka%fP{RUmfZclYsc#XMQ{Z|DGChUz(?O`Z0OK!RTMQ z+?(&|6yKgk+gL!sXL{P&+CRnU>7PGNT8Q0=)FMxA2fbM0T7ddYo%1+`)d4+`)u+W1 zbP&_N%Nqcejo`8p#>@P=Cq=u4%~|8c+@>)FepAfC>>@`twnSMJ|on#09d;3Tx99ffZ1=WCIAo{ ziEi)4R&QNF=jNtH*_zADgG$o;UA_j3?N97h1wWMAaaj=f4oRo*&+Bm(^a~&=LjP z`;)iu&43l(@pNzY>++{DDI@@5-hVre2S6ScF}#)icUW!I2GR4gtwWQxP8xRArVP5v zUm|Qmx|02|ZoWbXHQI}2MGsrgP%JnLw=r#&D!MiPQhaF{IWsGitNYg~>Wee0yQ>*P z=^O7JBxr8d2iBQa2$fpgDBjcfV>e-9k&FWVGY=Z{LLyOp8WsGza1*#u7U=S2h|d(Y zy%hIVtPDoX6AY6L>!PE$N&XJ zPes7cY}c4nKlll-l+{74c{z-RDJW+AHnAv;YsgcB1Xg3<9-FNr+RZ{y2F+!Z@JHmF z=%3SdUE8lT+^^&iXy8Pg$RgIZa*huQ4MH&kO|3at1&JSiN?dJyqP+5_ikXoNS!%b3 zsTsBHR(o-TLe|mhK!3*w$8A)r=Bnhbgj{nX?GVs6wA@^_LLxwhsG1Q16-=(% z^@;6IbfR~=-?#9kkmP6)n>WY@#;^|wylg5x`8ljXNiAnlVw%L!jpJrgS%F5rtpkCD zvWnUewXhz{3ZhuLi%!r()~gXCP9A-l8!IGUxGxur(LwPE{`kFF_w@XT7VZ&BzlGhJi~Jx zMmdxq*iw?H*;CJL7TC}gGpT0^wt{V$KPFAxID=|67(T8&DrW@t`fEhMf{b~s05Qe| z1YQTRf-3+BuYHD+<0z?b|A%doAeo}6QF&PTT1to?W_>~MOHv!m!7d>oMWe>iP&!%# zqv4SK4WFg+IQP%RJUG4cDHpM2%MyVp64162B9Q)JWRbuD9j9;TyId?p=2Sssrv!Ba znvy`B2Kx1Kr|0i}^uC-6w;{XzzLLNo7+`>z-;@pn;F13SRN^0q{p4>m(qF6BXo@=) z1G#5N!PY^d^o50ZF^agesHx&$o?>jZ^Qv`Ywkk==6H7lV5t_UjJFX}@TJekcLHgC_ zg1(rHRD&sC&FKUkuR44)oJUunAchMkI(jYA*kR#gd)uhHgX&+u+PS;G z);m{5oGzn$Qzjd?OQoqJTzRIZrg-cdqygCS2xD9pvB$N}|N631iunp$Y^PV7_@_6; zVrP+0d-c_KgXY)2fU$MY&A71ChDd?m%fq{9@$p5O1k>V%kmwi)c&{uzEp_l2o*~&B z?o=SoPrEs;XTTm5UHGk0ARLGv%*XDQ_?^rQt3=aX2cmXKq!xd))N1!!o84*J{w&|o zW1uqx`&lwPBl(>}%I*knsU1a5DigTBxOjgo_ceMi4HwwZ&iXJSzs2^l_}ql53%M7^ zy7sQ5IX1NOqw$w62}?RcBMN8gqXjIu$I&Og!N8!38UL$btoN>=6{H0?jgEeslm+El zH75l#(vnl9E)(7gd{CdF;YHs8?`w7b*O;hE5BBEfw)SGGmSSr4c5EkZMKb(8HgJ`= zEa7F4=dA|L^ZJDv)s1Re{C;sK04@GjWgt2OGC84pK&OA(W4SkzK8jLZTQ3+c;|S`S zH~BF5>2omL8~+nx5taJ(Ql)=&6(uFT=%Zo~@Hjg3covt{*Cu|}<4jQe?&+~RP5rlJ z$)afeFku!ANq~mRluDwG1FyOX(c|w!eOfS|zG2Iv7=0l|Lge#}Dfz$C^u7VdQcUQ; zGIj9Zg=!ROXDBe|U$wI)${ijrQyIy!z0+h_w6ZAP+6S7N)BZm$z%2Qm+EJSDz|YH> zSgoei+46`5dOQp{LX7Z4ppOYkSFz%6Fg3i##aK~seDW8=hAB$%6RxDr3(Ihq3Ofp$ zdEIZ+y}BCMMilA4=`&SmI+)ee5vih*0|o4i5`~@c&tbyd)UJbMaDc2qo+{SyYJhG1 z*K~rzU&DtPX`$Skaav8ouQM-+hNO_DMm}z{52P8uyY4#~4E6V3cMfdN|4dn4D4=yq z6}vY`hw>zoEd17ODb-%OsJ2{W8{Qicp`A5TIxCEqdZ^)=+s&ssGeAN+m7QpSerp?M zKOjd&=ON}d_;8$FYVS!2K~mp;I-b&yf`xe#kxr-_TXFuSCE?ZI-`ep;!z|GyC9gOw{2r|% zS}04^2{eo4 z^@|ZA#WU%*UK(xK@l~irmGYpzB`W*~0Emx5q6^O)9?9SXPiGo9>LIGlaDlENM&6GM znvCzlk3oyq{B|oj{B{?*U+%zCny>Wak9AnK1ZoFvMmL@O%N%S=etf05$>cu9_SOEx z>PwUFA~^o(oc=G=QzqK|eRM%m7h+8h-Fhr>&I(YpUE}C%lOtPSNidkEt%e8m$hM9S z3v@Bjo$reimu^54S+3p}6AoPtT{mXg8ZtACc;mcww{liI z*~)WG<>*+KS@ok7Q~m^De^a4(u{|3XH-qm@rslYdfoAjLyHHLOg%n zUla`ssnA?on~LjxB9?J8_WYx=a=!-@BoqJZiAGmQiRQlj?C_l4vgGu)N)XDylIyOm zojaW&p%7Hey10bdC%ACVzP&H~wJ*kFQawITWqfDb7Vdwy_$1vO-Axwm*Gypdz7i9v zs!9oNP{EnQ9DUG>zYp?Uns@72`>HO!ZQ?!We4Qx0NaH*F2Aom>_%;Mg@3Z?V)GszRqD7GlXeBl}|dyaBk+fCXzE%xfsS zWXom(jAB8rzc0p>DXp>+gDr4Bg{KM!PKmEThp7nq%LWiI?Od`G7QHUNl?H>NI_ zyO}r!xn$p%7g9>Mj78`w;cX0Tq2#S?W?I8-oN4_yW*=8<1p40C#LTeNN`+1?TK$01 zc&i&{qeaqsnW>`dmK%+#d|v;{;`aM%NZrvE3l-RyMMgQ8u=yfG{M1{K0@<^{2M7-V z+MOR3(7Zlwd&zDU$!z(-G!KNIQ1|2R@Ahz;odKTXT`I7?+;p@=cQA;<$JFt?CJaZ; zBbB?Qe4ri|%n?5%j2dsZzwh~ex$HMhFAC9X!AU(`TOs3b!;UmLWhlD=mPcKVXSeu% zD^tt?r^jtdl;yZQIy#m@HgFNw_Y(y)x*vpPUY89cXQA=Khrc_hAAWUz5}3#R_SG?_ zbfBn+AyC3Z*#O7#!vCGYk(wMt=!Uk+37vz3BU`M!7{PCB|9F2hIf=O99xN&afdcrd z+T5)^*w!j_XM*8kXw)P6EPPjjtjS_usc$gc+&D6E98l{tdj(OoY)KbeJ*&})53Cn* zMk;oj8=~8afS(5gee=%_dyWr+jy#una4sPi+~w1p+!fJOt|l=`C5yjOVKt zz721Kt59yN4od(MbJ|S#&DW?U;c_v>4A-m&U~g*}{5`(bYIefFe-X1v zA03LhvxuUxTmk`|<0D-4u+pNq4FWkqGegU|1d2=${ey*Ttb{ zhYbT8V!_1xGF_R1C%jM(=yC!r7GznHrb{7+dd1IEq@cxbBeYkc4l`7dv_=} zZ5FHLsht5C_4A9d5Gc6tk^py;qN}zxJvvMs3T6d>*6OVAJ10C3a*D>8!99W2131u1 zl|4ZT>7T?S_nlcm`tCR;hZxQ4joU%5!1rRoK%e_F$tiPPU6J(E3+U9f8pmvFC@K-x z)Ds7l;Uef_o^A45vO>sT;^lXG^f8l@&KxgQ_z~;K1LM2(Xr!`;F8-zeAu5cmjoWDu zGp$Xs!;wSlTI+&)9^B`3ujTF0D~51Lb38*oDa_5M|BD?gt88$AyPpv zZ2j*>o5usO?YG9anHzKf$ znAI~g*-bHtLgdNie*aNdb=*ar1TbrJCsOZOy-VVHiyP6&c0^I4j* z{#yQcjqp3dN!3&qkucP^7#0E}skld*aDH6Pj&p9f+ffC9)Vkkh1b6xYrH#O-B=_{#6Hm_5 z86y96_~RPy`y`+*l9d?cGLkGC@4EW>8FO5&Zz;Dxx-$UO^m9lK!$0zcNdG3VJB8{b z>b`={!ZZeU>jIg&FJBgJ$@u!q$U~R!9GmNaRdDz8?v)@}Y&CUw`ZMC!Vx4NZ`Sen3 zrxc21S;05PR}C4|VZg>sTg+vM)LDzo;rE#WY_`UeF(tQV3x#fWcr2lqGQ_^x(HxYZ8!}_Hg6wjUG|y?siV< z?-K1>J0CYTN55(mICn4TFZ{b55vv^|6{fn8knF?=mhCoXsrme&Iez?2F7k^sQP*g8 zoJB=&D_kfFn-l)=HfNkyD0ckk9RbugqPYxi+O^wP)KsEW9*k=XCxZx6FJE5k@3qd zR;%%2r|Ia1zR8ZaAt9Z*{H`cM&hzzUiy)Wh_@Ue~On4M3mrP*GlCke^{Q}dvp2u~W zzUg1%{>aEFQP?qngCuT^Z9u*PZb%&TATmAhd|q#XM+ZF@SjQ)p(m45ySV_wXo418c z&(vcY18Oaj6F;jsD#8p&==K1F zuD0_Y`YOoW*VO-q6x`mY8G+ywI{K=-Y4w?r&(O5?YHdd}Ezv72_OPLbXVuAGU_JW& zPZn<$7O+s)*X&o6tp`+&+M@~g9P|B+bJ;Ej_J+cm)LUIvQ*e8MFgmXQo{ckA7z}cL zUU`aScQ^i};AKo!c+IhNe_8V<*J@w2)nX8%K20hhSkt;|jX!>nT8=}$bKi}6;lwkg z+xZil8QP}s6C@^|%$&QSqwe*1I=tF&oez3xNXh>`)%#|eE7nBY-^}G^12oO0+aYO5 z?Xeooi>`9$<+|DK*ajA%C5N1byd)wRlfnr(f{MSNxh7_mGkps}(Q!KZy1RGU&1e(( z{?2uz!yfSp$r&`AR8TLY$$tlaOVw9rj$-n>b02xLnQ2cBd?~~~RA#PR$P+V72hDX9 zMi`RkJ44@42tfM|$Kb#At8Czd3<@D=-=Q5)U6`1rf7koZB64g>7-HyU#3wt)E@k8= z#~-;&ZG0rnxvfSr&jyN6#@uFgx_Ol^2&#%gyyRS8GwT7s*RhI_B0~nQi6o0f|HGZQ%!i5Ph+)UHhcq}ux(?{#C&fgz&2(^H3ZxVdN_%e+*2W$r@c=yj1i zr=&G^wYAmFX{;kSSo)nj10v`fJsHiRK8(6}^|ad|j@e>Gyl_oS_8O9~%i06O7=PTF zg7zX}<)HRLof3MfA=C4YC#p99KQ8Z9Uw&(XTIj#DK*X#N1Px!0#tf1}unoUPQ+-^m?ryt|RFDpjZ)KV3&*2vYfJcz!l=@3n6>T;W>6v9*IKL9)>D zZi_QfU%}!AHe-7;d7=C1(+4VND0z5gC=L}jx>+$zPPm3Q{KS)ebVdOegCa4Cfu%dE zRB-#r8z4JXlNJ~RJq@)AF8n2AhE-cdpo#Tanje9=ytF)j-HAP_{t`20WY=taVr71n z@Hqj?P^md7ub%Tsdy6kwW`#CX&974>;y)I~Pkod@!tJOH{_w{at)(_V*&o+g z3T)D`=Go9NfXM?h2)A(1Rr(~w%zB+snIabz6qDECTy(EvSb8V85 z6V~zsp-zon2d_xw zcfK{NKy%~9oZ7L%mB@klUdkPv#S{gSD?Y!Xo=v+!*Er~6qd9&(wV}*ZNUt5c*M=ga zhcc#4f1i>1AENfp742KgFW@2aF^n$q?2uEM;fQCU>%Pu4U%j==bQh;gOlUIrS+$+< z_|UEEP6{V93g}}|r`tMQYrsYN47yjn5AMdo!+Og#u}3_C`R;VFXWL95Gnb$W4Lpq= zy+7V8xFpUY4TWoPBFxs#^4dM$^=>~mk+1*&NfFju9-F7?=3Gbkpdh{k_b2rmlzp#R z%U&Uej~04dTg`vV?6}Q-xdb0(5C86NH&>lafZ>aUDdwa{4dk_6-rG+Eb|Its*junp zP`1Zq@Ghkni>Ma;61X;furQzlHtZ(zYZSp<*?nrS~QH<1ngS6MX7v;3c_Lu{IL9k{j*4|Xa`RC zVv_^aGX-~?HooR%FA0|lvHN?kQHpvJi#qj)Nr#b4M?B!jmGBkCF>HjGp40qYwKGKI zxu*X*x_1nS1%$!kJLXF|$%;Yxr9~BIYcno>TNGFJJ^Pa3G^eKlB{v%1j~{%^;ktno)iuw}f96Uh z^@;I{VDW~%lgwfx)cq&MH7J@_+k1aRrZqc&o`cn;0jnMSIvjuvnLlw&76oKe<<#=s(QJK zjF1z7T~@ILk@M+;Qn(O4B~L2P>%91NxXhIGt1ddq&sT>PEKq9HENoNDx}B`x@6;(a zH-RM}&450@zYkT1K6$}#5#h%Q=OX$>G#EH!+NMkxQ#a=YM07DX-{6C-%15GAw2u$B zK20xUM}3bu@$7HF)Uj`$=c_hk=eys0IY5MVZ|G=3D>sY&d=&1ZkA08`(N#bgwoKHS zySdr0{(R;d6vmf)IGe?3Fl+oU4{x$>ZS;sC11g73`sOqCzuDst4yrV@sjPlw3a)c& zs~4bUq;h{0sRKay)r~i3epX{dUmebo?5y}sy+A+%IvPIRmrabuf6fVGi*?bmiKP-G z&{aW9>8^#?<5K((5pK6%fzK2(&+ImWyDn3VI;+x;{>IuRO)|7?5o-kuhtgj>yA z66G_tJd8kwk-$T_68o|Y?8bBSsQO^A_jc<%%q$CAB*4f8mOr4uD6`Yu>e8Zfwe2A! zRX*I1DuElWx@2;Z0}?Z=J=J#V)?M>@bA^{nK|fHz_D4io@1x6FN2k~DTbwox z9sfH4%7pe{+z6L6BW6nLrls$d2k8DAgMLv18%)Rv?L?@@HC#m0Qi)+&w}7L|C-$W% z1?f~*LAD*Nn?O3XPoFBmVQUHifle2lJ7SOB4W1wQql2y065h9WU{ zLwlFw^o8@@4`ceIGvWnmw)d+juPdo}eG9C+^6-+D4$`MrW+6m#zqWIaxR2F4o*wU}MLi&DP&p|XDJiK?2NrclKE9+@ zlp`dK`fplrF-#!3W23%)$&jF!TK6<=#-^l%%ke9}-dk<7xI;hKT?s)5O`hw`-&o^gMVm8}IpZV2jLSBM2VL3b*Jz%n7*YF_p zfr&s_jXCT^vsR9_P1+yk*U>M0$~2DKm!MAKo=>D!N&&$02Bk+p~bIszfE1)9Xlv`H!m?2OtpO~?~J*K-fzOaFgV zePvu!VfQUCFwz~v00PoINFyoTAT8kxostq#Lk$Rngd(Y=G}4IDgA5>@64Hp20)lkh ze`qy9P_grt#=f=kG^#k3WJ_Cqp9i0%$H zsE#tLHbaz}k~k97)*JZ2l*g#nFZL&%#Vl@eq@bNL)YJ@;!5*KDCr-X_PK9ozt(*%Y zb=lHjgne_(6@SDWSG;N~W9n+c%^g)xPi&7RB`g9w=!E-ziOR>tjBidF*w5ooRX-&j zo?`g-uT45?zM3kCvM}-2bo(86>a-q?U4o;&C_no7{8U)(n;coD)6~60i+Ijqn^?Ras~L*6+6O2-pt7yjHutKTy3YH5HSFCZ8u#4`>rH z`}v;Ry?6gXdqzxHM6Dv|hxYfT-=A|+U%7tYoq~x!m)x}4HNWpbB^$<VtkvWjqO(OngQjhm)W>_#@`r_M(h&W{)tj zCqC&xl6y96fLA5C~y&VZZBdX zEssb3y4~o+txOs;RC%zXcvBWbb+p8IX&%+5MDJ4Eu{FP!{)Y(Uy2lCW$Mn|%O_C&K z3k~V0{cQ)f4>Dh(?D|tE3rKo!ApIOTMX#-`>OJP}|C${Fvy)+zF)oy_j$#D;u3(il z#I7~_E|65ebmL_~ou`WmKOst6Da5%OC|`c?;TKD<7A5Ixa2#UG+{T%TFbPK>NKnxG z9mB&TuR45knC{2bJL-S#HP70DldSZ37z0ZIrckwv<;3MapM;bj@#*_CdIAl+5GM$W3eMq7_KgOQ+2J)HI z2BnTiW8M;EhvIv{j8tU^wBvj0E4Vk1I>?|&*~wVc-CxC~q5AwbLLeG@)5s4ZvDYUb zJGtn+Z-uV?2tRo~EnHEr?Ki$#xB*o%nnvti@P(DUM43)C|Ts;_HEx1qHL!o@r$H_JnfXX$;nl; zikjR`ndwW2R381|3>Q%^?3nh$C+qXSX2)IsNFfhYaV|@Cgx@=bt6%#st8kKz;n$xX zs5~Is`P%E2A?h*41BzdL7m|-oQ{r$6}2xsbie9GHF-;vLG%`|PHODn>EAw~Rs)~jc0iincy{8M+ zEeu+5eOgi63-1(G5hP6t%BOb5Cx-%o zn{Gy|aQ$Y_1Qm67v0JmR_yxc_;6;C=N%w~-teUCUH{&)_aRA#RQ)jZFJ^bD4Zr>vm6Ohp#uD+zKgSsr5!JDv(_GoV@|k=~dLfIS8D4-ZQ((0@7-kmi$6SKa z!)m0Di{cv4p|nA{Fp<{y2wn^b?MPXLX~JTb+32M^^R3vE^6E8Lc#V05n+>+3kY9TJ zOmlLdEO0N1{>Z;bp%3*Tl0#u1MjN>hbM#+g=cQ&QSd|bDPw$X!;sXRQ0Au!-9 zn^=5dy&hL@|xuH4ehFXYAE~N5&#@)D3U*?UG~hD+(*zCS^ii=PYr{%eN=>Vb^9w zOf6;`vsVakdoI6Tj5&<57$eAu6JLUtkgc>Gh?*cAh8< z7sMU$JvC@TYzfofep@~%@=hV_qPLkIVhxc+d*@T#y*pxLy-YK*p|;SuTx%o6{e?Zk zUZkRcE|6)f+shZC)f69nSkl17l{NpDXj=+_iLtmtfg<0@Otx)T2Q|>I;1Hit-Vq_F z^J8EH6z~?x_1@H6(-u>KSRaoj>WjYUFQn;Gg4$ZkV!KaI+0msh2>4XG2`#X}L)7fG z*tx~e5|WYuAnH~%KG5b|D@6yn9?6-Pq^(G8)IdL?=I=1tVyu}7(?{OJlH zN=}}{=2@;RD5)K;xShQa9wO8?Yc=~~v7~2(K)N@LAO$c0mE2kDj{GTX`@NWnKY9G; zq(PFTY@&Xjon1g*k3r&#?ZyWvxS>rxXMBj)}p=nB+2 zN=0g2v8gc-YUl?>3iiG>bGSI&PO8 zlt*@Q7u`R#h(4{<9%hu**-3KGLgGE;_ZNtr*vg>hv((LGgFEak=?Uh-X7zh!TVKr) zdxPmH9{mn6HX84(h|VYWUtyqd!<^9q5^T@`vi~h+>{yuJE9(QsW$%^OBcC>xWViXQ z;(nTzjDPDj8*#jK>vz+(yp-|oS*a53t8e26;9CwrxSDK5mZr5-KyO7MmWew;{a_SFQOU)C2q{IoCX&q%wv#?chNCDPb~ z*q*KV83DE0im(#<gQkpliJu^JB z@){=BwVwq?KaQDWi?Ktn7y7YT~ETj|B4;3a7*-(Kcnzgrq+ATgfONpUx zr~3Iac9e473G=VzVyc|A5sx`a)O)fk5;UiLwvo?A8d68D!ol@y-1T(vOr2J}3~CJ} z#UCH*!oeB|lc9K9Ult?066r`&6f${?BoiN({UyY};$SeuOF`4+h-xVUO+W-@!A*@oql!7wTjP zUvD53o!&Wy$YYKBc0Q7{f5bAEM}BB6GKKUilGdm1Fvpw|lt$iQ{FgnuET=3IpJ_rU zRarpLw^xCfkLJsf%;JtQC|^h%Cs|A+X6pk=531;hLzq84$b{{?I=79gQ?h4Az)m1Z zO2qn64?p{#Pv+g=W4026Lt{uw*yJ8&7%93?Dr)-hC@p{Tv+H{q5~!bBMr5ybn8wO% z*_k-1Anf9CzcduK>^}L^*s6~FU#-tnOtn1FkxVB1$4$)Xx`75&co>5eJ-s?NDaM6u z5<@5|3%Xn4hT9~e@SKt0pQHQJ?h1=3=?PER;)qo8k)n|jrI?fyT8G0@q75d`Et|PL^PoBJfKX z`%-$J&XgOsc}m9dcATp_-d|a;5a?K0K01;CCZ;bnKS`1k2@v>>y&i9G{r*&5ll14D zCayjk6?hBJ@Hi@`))t>b?%jI420b%4#N!L06g0@e_|c;{U8m@AuZJ1JloP%bcd4lv zF$h|f7>BMV;Z4|MgYTa_7e;1i9z312g!F$+SDTjcXE0?D`TC^KzAI+*ys7m({v(9% z9xksWAmZU+(#;#7?{$!5pg@()%0A!W@ja9E0zZt4em+`~oF!WT!JI1iQWFv%_3`u} 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 v#Nkl@DtKo--E+XDH4hNB{}CE#|2!L zp^ljZ1@C2Jqb`AP28Nuk`Xv|~L%=ZW)awYmg{ufW!4W)<-8G*Iz-REe3mgR`xCGWa z{S92TgxK~CT)q9+_5$3b?XYOf;Z>m7-n{Ew;Pm|FXO{%b;Z(o{P9;(#5>d new PokemonHeldItemModifierType('Focus Band', 'Adds a 10% chance to survive with 1 HP after being damaged enough to faint', (type, args) => new Modifiers.SurviveDamageModifier(type, (args[0] as Pokemon).id)), + QUICK_CLAW: () => new PokemonHeldItemModifierType('Quick Claw', 'Adds a 10% chance to move first regardless of speed (after priority)', + (type, args) => new Modifiers.BypassSpeedChanceModifier(type, (args[0] as Pokemon).id)), + KINGS_ROCK: () => new PokemonHeldItemModifierType('King\'s Rock', 'Adds a 10% chance an attack move will cause the opponent to flinch', (type, args) => new Modifiers.FlinchChanceModifier(type, (args[0] as Pokemon).id)), @@ -1087,6 +1090,7 @@ const modifierPool: ModifierPool = { new WeightedModifierType(modifierTypes.SOOTHE_BELL, 4), new WeightedModifierType(modifierTypes.ABILITY_CHARM, 6), new WeightedModifierType(modifierTypes.FOCUS_BAND, 5), + new WeightedModifierType(modifierTypes.QUICK_CLAW, 3), new WeightedModifierType(modifierTypes.KINGS_ROCK, 3), new WeightedModifierType(modifierTypes.LOCK_CAPSULE, 3), new WeightedModifierType(modifierTypes.SUPER_EXP_CHARM, 10), @@ -1138,6 +1142,7 @@ const trainerModifierPool: ModifierPool = { new WeightedModifierType(modifierTypes.REVIVER_SEED, 2), new WeightedModifierType(modifierTypes.FOCUS_BAND, 2), new WeightedModifierType(modifierTypes.LUCKY_EGG, 4), + new WeightedModifierType(modifierTypes.QUICK_CLAW, 1), new WeightedModifierType(modifierTypes.GRIP_CLAW, 1), new WeightedModifierType(modifierTypes.WIDE_LENS, 1), ].map(m => { m.setTier(ModifierTier.ROGUE); return m; }), @@ -1198,6 +1203,7 @@ const dailyStarterModifierPool: ModifierPool = { new WeightedModifierType(modifierTypes.GRIP_CLAW, 5), new WeightedModifierType(modifierTypes.BATON, 2), new WeightedModifierType(modifierTypes.FOCUS_BAND, 5), + new WeightedModifierType(modifierTypes.QUICK_CLAW, 3), new WeightedModifierType(modifierTypes.KINGS_ROCK, 3), ].map(m => { m.setTier(ModifierTier.ROGUE); return m; }), [ModifierTier.MASTER]: [ diff --git a/src/modifier/modifier.ts b/src/modifier/modifier.ts index 8a5fba17d1c..0736831a01e 100644 --- a/src/modifier/modifier.ts +++ b/src/modifier/modifier.ts @@ -731,6 +731,40 @@ export class SurviveDamageModifier extends PokemonHeldItemModifier { } } +export class BypassSpeedChanceModifier extends PokemonHeldItemModifier { + constructor(type: ModifierType, pokemonId: integer, stackCount?: integer) { + super(type, pokemonId, stackCount); + } + + matchType(modifier: Modifier) { + return modifier instanceof BypassSpeedChanceModifier; + } + + clone() { + return new BypassSpeedChanceModifier(this.type, this.pokemonId, this.stackCount); + } + + shouldApply(args: any[]): boolean { + return super.shouldApply(args) && args.length === 2 && args[1] instanceof Utils.BooleanHolder; + } + + apply(args: any[]): boolean { + const pokemon = args[0] as Pokemon; + const bypassSpeed = args[1] as Utils.BooleanHolder; + + if (!bypassSpeed.value && pokemon.randSeedInt(10) < this.getStackCount()) { + bypassSpeed.value = true; + return true; + } + + return false; + } + + getMaxHeldItemCount(pokemon: Pokemon): integer { + return 3; + } +} + export class FlinchChanceModifier extends PokemonHeldItemModifier { constructor(type: ModifierType, pokemonId: integer, stackCount?: integer) { super(type, pokemonId, stackCount); diff --git a/src/phases.ts b/src/phases.ts index a802582cb28..88957ba1636 100644 --- a/src/phases.ts +++ b/src/phases.ts @@ -6,7 +6,7 @@ import { allMoves, applyMoveAttrs, BypassSleepAttr, ChargeAttr, applyFilteredMov import { Mode } from './ui/ui'; import { Command } from "./ui/command-ui-handler"; import { Stat } from "./data/pokemon-stat"; -import { BerryModifier, ContactHeldItemTransferChanceModifier, EnemyAttackStatusEffectChanceModifier, EnemyPersistentModifier, EnemyStatusEffectHealChanceModifier, EnemyTurnHealModifier, ExpBalanceModifier, ExpBoosterModifier, ExpShareModifier, ExtraModifierModifier, FlinchChanceModifier, FusePokemonModifier, HealingBoosterModifier, HitHealModifier, LapsingPersistentModifier, MapModifier, Modifier, MultipleParticipantExpBonusModifier, PersistentModifier, PokemonExpBoosterModifier, PokemonHeldItemModifier, PokemonInstantReviveModifier, SwitchEffectTransferModifier, TempBattleStatBoosterModifier, TurnHealModifier, TurnHeldItemTransferModifier, MoneyMultiplierModifier, MoneyInterestModifier, IvScannerModifier, LapsingPokemonHeldItemModifier, PokemonMultiHitModifier, PokemonMoveAccuracyBoosterModifier, overrideModifiers, overrideHeldItems } from "./modifier/modifier"; +import { BerryModifier, ContactHeldItemTransferChanceModifier, EnemyAttackStatusEffectChanceModifier, EnemyPersistentModifier, EnemyStatusEffectHealChanceModifier, EnemyTurnHealModifier, ExpBalanceModifier, ExpBoosterModifier, ExpShareModifier, ExtraModifierModifier, FlinchChanceModifier, FusePokemonModifier, HealingBoosterModifier, HitHealModifier, LapsingPersistentModifier, MapModifier, Modifier, MultipleParticipantExpBonusModifier, PersistentModifier, PokemonExpBoosterModifier, PokemonHeldItemModifier, PokemonInstantReviveModifier, SwitchEffectTransferModifier, TempBattleStatBoosterModifier, TurnHealModifier, TurnHeldItemTransferModifier, MoneyMultiplierModifier, MoneyInterestModifier, IvScannerModifier, LapsingPokemonHeldItemModifier, PokemonMultiHitModifier, PokemonMoveAccuracyBoosterModifier, overrideModifiers, overrideHeldItems, BypassSpeedChanceModifier } from "./modifier/modifier"; import PartyUiHandler, { PartyOption, PartyUiMode } from "./ui/party-ui-handler"; import { doPokeballBounceAnim, getPokeballAtlasKey, getPokeballCatchMultiplier, getPokeballTintColor, PokeballType } from "./data/pokeball"; import { CommonAnim, CommonBattleAnim, MoveAnim, initMoveAnim, loadMoveAnimAssets } from "./data/battle-anims"; @@ -1970,6 +1970,14 @@ export class TurnStartPhase extends FieldPhase { const field = this.scene.getField(); const order = this.getOrder(); + const battlerBypassSpeed = {}; + + this.scene.getField(true).filter(p => p.summonData).map(p => { + const bypassSpeed = new Utils.BooleanHolder(false); + this.scene.applyModifiers(BypassSpeedChanceModifier, p.isPlayer(), p, bypassSpeed); + battlerBypassSpeed[p.getBattlerIndex()] = bypassSpeed; + }); + const moveOrder = order.slice(0); moveOrder.sort((a, b) => { @@ -1994,6 +2002,9 @@ export class TurnStartPhase extends FieldPhase { if (aPriority.value !== bPriority.value) return aPriority.value < bPriority.value ? 1 : -1; } + + if (battlerBypassSpeed[a].value !== battlerBypassSpeed[b].value) + return battlerBypassSpeed[a].value ? -1 : 1; const aIndex = order.indexOf(a); const bIndex = order.indexOf(b); From 3ef08e433a2e959a543bd14fa5f8e8d99e770d05 Mon Sep 17 00:00:00 2001 From: karl-police Date: Wed, 15 May 2024 15:35:48 +0200 Subject: [PATCH 05/46] Correct a translation due to misleading token --- src/locales/de/battle.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/locales/de/battle.ts b/src/locales/de/battle.ts index ca0e60bf94c..1dc7b68fd7d 100644 --- a/src/locales/de/battle.ts +++ b/src/locales/de/battle.ts @@ -43,7 +43,7 @@ export const battle: SimpleTranslationEntries = { "noEscapeTrainer": "Du kannst nicht\naus einem Trainerkampf fliehen!", "noEscapePokemon": "{{pokemonName}}'s {{moveName}}\nverhindert {{escapeVerb}}!", "runAwaySuccess": "Du bist entkommen!", - "runAwayCannotEscape": 'Flucht unmöglich!', + "runAwayCannotEscape": 'Flucht gescheitert!', "escapeVerbSwitch": "auswechseln", "escapeVerbFlee": "flucht", "skipItemQuestion": "Bist du sicher, dass du kein Item nehmen willst?", From 3aeef5050725e535915265352855aa41dec8233f Mon Sep 17 00:00:00 2001 From: Alessandro Bruzzese <69127023+Bruzzii@users.noreply.github.com> Date: Wed, 15 May 2024 16:08:32 +0200 Subject: [PATCH 06/46] Update Italian starter-select-ui-handler.ts (#901) --- src/locales/it/starter-select-ui-handler.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/locales/it/starter-select-ui-handler.ts b/src/locales/it/starter-select-ui-handler.ts index 79c2e26c642..af95fc374bf 100644 --- a/src/locales/it/starter-select-ui-handler.ts +++ b/src/locales/it/starter-select-ui-handler.ts @@ -29,7 +29,7 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "cycleVariant": 'V: Alterna Variante', "enablePassive": "Attiva Passiva", "disablePassive": "Disattiva Passiva", - "locked": "Locked", - "disabled": "Disabled", - "uncaught": "Uncaught" + "locked": "Bloccato", + "disabled": "Disabilitato", + "uncaught": "Non Catturato" } \ No newline at end of file From 3c8d919ef8e1e69a063710e4d98cb27a0350d208 Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 10:13:29 -0400 Subject: [PATCH 07/46] Revert "Implemented Power Split and Guard Split (#699)" This reverts commit 0b75a5210aea737e18acbbadfe3013fed30136df. --- src/data/move.ts | 84 +------------------------------------- src/field/pokemon.ts | 22 +--------- src/system/pokemon-data.ts | 1 - 3 files changed, 3 insertions(+), 104 deletions(-) diff --git a/src/data/move.ts b/src/data/move.ts index aa722b29e5d..46216eb754a 100644 --- a/src/data/move.ts +++ b/src/data/move.ts @@ -2005,86 +2005,6 @@ export class HpSplitAttr extends MoveEffectAttr { } } -/** - * Attribute used for moves which split the user and the target's offensive raw stats. - * @extends MoveEffectAttr - * @see {@link apply} -*/ -export class PowerSplitAttr extends MoveEffectAttr { - - /** - * Applying Power Split to the user and the target. - * @param user The pokemon using the move. {@link Pokemon} - * @param target The targeted pokemon of the move. {@link Pokemon} - * @param move The move used. {@link Move} - * @param args N/A - * @returns True if power split is applied successfully. - */ - apply(user: Pokemon, target: Pokemon, move: Move, args: any[]) : Promise { - return new Promise(resolve => { - - if (!super.apply(user, target, move, args)) - return resolve(false); - - const infoUpdates = []; - - const attackValue = Math.floor((target.getStat(Stat.ATK) + user.getStat(Stat.ATK)) / 2); - user.changeSummonStat(Stat.ATK, attackValue); - infoUpdates.push(user.updateInfo()); - target.changeSummonStat(Stat.ATK, attackValue); - infoUpdates.push(target.updateInfo()); - - const specialAttackValue = Math.floor((target.getStat(Stat.SPATK) + user.getStat(Stat.SPATK)) / 2); - user.changeSummonStat(Stat.SPATK, specialAttackValue); - infoUpdates.push(user.updateInfo()); - target.changeSummonStat(Stat.SPATK, specialAttackValue); - infoUpdates.push(target.updateInfo()); - - return Promise.all(infoUpdates).then(() => resolve(true)); - }); - } -} - -/** - * Attribute used for moves which split the user and the target's defensive raw stats. - * @extends MoveEffectAttr - * @see {@link apply} -*/ -export class GuardSplitAttr extends MoveEffectAttr { - /** - * Applying Guard Split to the user and the target. - * @param user The pokemon using the move. {@link Pokemon} - * @param target The targeted pokemon of the move. {@link Pokemon} - * @param move The move used. {@link Move} - * @param args N/A - * @returns True if power split is applied successfully. - */ - apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): Promise { - return new Promise(resolve => { - if (!super.apply(user, target, move, args)) - return resolve(false); - - const infoUpdates = []; - - const defenseValue = Math.floor((target.getStat(Stat.DEF) + user.getStat(Stat.DEF)) / 2); - user.changeSummonStat(Stat.DEF, defenseValue); - infoUpdates.push(user.updateInfo()); - target.changeSummonStat(Stat.DEF, defenseValue); - infoUpdates.push(target.updateInfo()); - - const specialDefenseValue = Math.floor((target.getStat(Stat.SPDEF) + user.getStat(Stat.SPDEF)) / 2); - user.changeSummonStat(Stat.SPDEF, specialDefenseValue); - infoUpdates.push(user.updateInfo()); - target.changeSummonStat(Stat.SPDEF, specialDefenseValue); - infoUpdates.push(target.updateInfo()); - - - return Promise.all(infoUpdates).then(() => resolve(true)); - }); - } - -} - export class VariablePowerAttr extends MoveAttr { apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { //const power = args[0] as Utils.NumberHolder; @@ -5744,9 +5664,9 @@ export function initMoves() { .target(MoveTarget.USER_SIDE) .unimplemented(), new StatusMove(Moves.GUARD_SPLIT, Type.PSYCHIC, -1, 10, -1, 0, 5) - .attr(GuardSplitAttr), + .unimplemented(), new StatusMove(Moves.POWER_SPLIT, Type.PSYCHIC, -1, 10, -1, 0, 5) - .attr(PowerSplitAttr), + .unimplemented(), new StatusMove(Moves.WONDER_ROOM, Type.PSYCHIC, -1, 10, -1, 0, 5) .ignoresProtect() .target(MoveTarget.BOTH_SIDES) diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index 8d6b11ae9f5..48287cf39cb 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -544,17 +544,8 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { }); } - /** - * Returns the value of the specified stat. - * @param stat Stat to get the value of. {@link Stat} - * @returns The value of the stat. If the pokemon is already summoned, it uses those values, otherwise uses the base stats. - */ getStat(stat: Stat): integer { - if (!this.summonData) { - return this.stats[stat]; - } - - return this.summonData.stats[stat]; + return this.stats[stat]; } getBattleStat(stat: Stat, opponent?: Pokemon, move?: Move, isCritical: boolean = false): integer { @@ -1717,16 +1708,6 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { return healAmount; } - /** - * Sets a specific stat to a specific value. - * Used for summon data, while the pokemon is out until the next time it is retrieved. - * @param stat Stat to change. {@link Stat} - * @param value Amount to set the stat to. - */ - changeSummonStat(stat: Stat, value: integer) : void { - this.summonData.stats[stat] = value; - } - isBossImmune(): boolean { return this.isBoss(); } @@ -2185,7 +2166,6 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { if (!this.battleData) this.resetBattleData(); this.resetBattleSummonData(); - this.summonData.stats = this.stats; if (this.summonDataPrimer) { for (let k of Object.keys(this.summonData)) { if (this.summonDataPrimer[k]) diff --git a/src/system/pokemon-data.ts b/src/system/pokemon-data.ts index dcf4a5744b6..dfbb9be570b 100644 --- a/src/system/pokemon-data.ts +++ b/src/system/pokemon-data.ts @@ -112,7 +112,6 @@ export default class PokemonData { this.summonData = new PokemonSummonData(); if (!forHistory && source.summonData) { this.summonData.battleStats = source.summonData.battleStats; - this.summonData.stats = source.summonData.stats; this.summonData.moveQueue = source.summonData.moveQueue; this.summonData.disabledMove = source.summonData.disabledMove; this.summonData.disabledTurns = source.summonData.disabledTurns; From d32dbddd480428327cce39b7cd1820426dde8da6 Mon Sep 17 00:00:00 2001 From: mbroll <39443552+mbroll@users.noreply.github.com> Date: Wed, 15 May 2024 09:21:52 -0500 Subject: [PATCH 08/46] Update ability.ts (#910) Water bubble should double the damage of water moves. The current multiplier in-game is x1. --- src/data/ability.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/data/ability.ts b/src/data/ability.ts index 0ff03ed6776..a257525efd0 100644 --- a/src/data/ability.ts +++ b/src/data/ability.ts @@ -3456,7 +3456,7 @@ export function initAbilities() { .attr(MovePowerBoostAbAttr, (user, target, move) => user.scene.currentBattle.turnCommands[target.getBattlerIndex()].command === Command.POKEMON, 2), new Ability(Abilities.WATER_BUBBLE, 7) .attr(ReceivedTypeDamageMultiplierAbAttr, Type.FIRE, 0.5) - .attr(MoveTypePowerBoostAbAttr, Type.WATER, 1) + .attr(MoveTypePowerBoostAbAttr, Type.WATER, 2) .attr(StatusEffectImmunityAbAttr, StatusEffect.BURN) .ignorable(), new Ability(Abilities.STEELWORKER, 7) From adf5690383299c4902655eea32018f26f06b093a Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 10:55:17 -0400 Subject: [PATCH 09/46] Migrate data for offline users --- src/account.ts | 11 ++++++++++- src/system/game-data.ts | 1 - 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/src/account.ts b/src/account.ts index 357cd5af4cf..f5d4e2858b4 100644 --- a/src/account.ts +++ b/src/account.ts @@ -14,13 +14,22 @@ export function updateUserInfo(): Promise<[boolean, integer]> { if (bypassLogin) { loggedInUser = { username: 'Guest', lastSessionSlot: -1 }; let lastSessionSlot = -1; - for (let s = 0; s < 2; s++) { + for (let s = 0; s < 5; s++) { if (localStorage.getItem(`sessionData${s ? s : ''}_${loggedInUser.username}`)) { lastSessionSlot = s; break; } } loggedInUser.lastSessionSlot = lastSessionSlot; + // Migrate old data from before the username was appended + [ 'data', 'sessionData', 'sessionData1', 'sessionData2', 'sessionData3', 'sessionData4' ].map(d => { + if (localStorage.hasOwnProperty(d)) { + if (localStorage.hasOwnProperty(`${d}_${loggedInUser.username}`)) + localStorage.setItem(`${d}_${loggedInUser.username}_bak`, localStorage.getItem(`${d}_${loggedInUser.username}`)); + localStorage.setItem(`${d}_${loggedInUser.username}`, localStorage.getItem(d)); + localStorage.removeItem(d); + } + }); return resolve([ true, 200 ]); } Utils.apiFetch('account/info', true).then(response => { diff --git a/src/system/game-data.ts b/src/system/game-data.ts index e7ffd281b04..c635d66c1f1 100644 --- a/src/system/game-data.ts +++ b/src/system/game-data.ts @@ -355,7 +355,6 @@ export class GameData { if (cachedSystemDataStr) { let cachedSystemData = this.parseSystemData(cachedSystemDataStr); - console.log(cachedSystemData.timestamp, systemData.timestamp) if (cachedSystemData.timestamp > systemData.timestamp) { console.debug('Use cached system'); systemData = cachedSystemData; From 9b8af7ad718234089e50a4dd7e7f8723d50bc50d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Ricardo=20Fleury=20Oliveira?= Date: Wed, 15 May 2024 12:13:35 -0300 Subject: [PATCH 10/46] Fixed the ptBR text in starter menu popping out of the info box... (#902) * Fixes the ptBR text in starter menu popping out of the info box and added language personalization, changed some ptBR natures and ordered thw switch case in alphabetic order * Small fix --- src/locales/pt_BR/nature.ts | 4 +- .../pt_BR/starter-select-ui-handler.ts | 10 ++-- src/ui/starter-select-ui-handler.ts | 47 +++++++++++++++---- 3 files changed, 44 insertions(+), 17 deletions(-) diff --git a/src/locales/pt_BR/nature.ts b/src/locales/pt_BR/nature.ts index b78168f13c8..3cb33340e2c 100644 --- a/src/locales/pt_BR/nature.ts +++ b/src/locales/pt_BR/nature.ts @@ -8,7 +8,7 @@ export const nature: SimpleTranslationEntries = { "Naughty": "Teimosa", "Bold": "Corajosa", "Docile": "Dócil", - "Relaxed": "Descontraída", + "Relaxed": "Relaxada", "Impish": "Inquieta", "Lax": "Relaxada", "Timid": "Tímida", @@ -20,7 +20,7 @@ export const nature: SimpleTranslationEntries = { "Mild": "Mansa", "Quiet": "Quieta", "Bashful": "Atrapalhada", - "Rash": "Imprudente", + "Rash": "Rabugenta", "Calm": "Calma", "Gentle": "Gentil", "Sassy": "Atrevida", diff --git a/src/locales/pt_BR/starter-select-ui-handler.ts b/src/locales/pt_BR/starter-select-ui-handler.ts index ba180c2cfb2..4e0f5ca73f9 100644 --- a/src/locales/pt_BR/starter-select-ui-handler.ts +++ b/src/locales/pt_BR/starter-select-ui-handler.ts @@ -8,9 +8,9 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam": 'Começar com esses Pokémon?', "growthRate": "Crescimento:", - "ability": "Hab.:", + "ability": "Habilidade:", "passive": "Passiva:", - "nature": "Nature:", + "nature": "Natureza:", "eggMoves": "Mov. de Ovo", "start": "Iniciar", "addToParty": "Adicionar à equipe", @@ -25,11 +25,11 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "cycleForm": 'F: Mudar Forma', "cycleGender": 'G: Mudar Gênero', "cycleAbility": 'E: Mudar Habilidade', - "cycleNature": 'N: Mudar Nature', + "cycleNature": 'N: Mudar Natureza', "cycleVariant": 'V: Mudar Variante', "enablePassive": "Ativar Passiva", "disablePassive": "Desativar Passiva", - "locked": "Bloqueado", - "disabled": "Desativado", + "locked": "Bloqueada", + "disabled": "Desativada", "uncaught": "Não capturado" } \ No newline at end of file diff --git a/src/ui/starter-select-ui-handler.ts b/src/ui/starter-select-ui-handler.ts index 8443ed5741e..6017438e013 100644 --- a/src/ui/starter-select-ui-handler.ts +++ b/src/ui/starter-select-ui-handler.ts @@ -245,30 +245,54 @@ export default class StarterSelectUiHandler extends MessageUiHandler { this.pokemonUncaughtText.setOrigin(0, 0); this.starterSelectContainer.add(this.pokemonUncaughtText); - this.pokemonAbilityLabelText = addTextObject(this.scene, 6, 127, i18next.t("starterSelectUiHandler:ability"), TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + let starterInfoXPosition = 31; // Only text + // The position should be set per language + const currentLanguage = i18next.language; + switch (currentLanguage) { + case 'pt_BR': + starterInfoXPosition = 32; + break; + default: + starterInfoXPosition = 31; + break + } + + let starterInfoTextSize = '56px'; // Labels and text + // The font size should be set per language + // currentLanguage is already defined + switch (currentLanguage) { + case 'pt_BR': + starterInfoTextSize = '47px'; + break; + default: + starterInfoTextSize = '56px'; + break + } + + this.pokemonAbilityLabelText = addTextObject(this.scene, 6, 127, i18next.t("starterSelectUiHandler:ability"), TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonAbilityLabelText.setOrigin(0, 0); this.pokemonAbilityLabelText.setVisible(false); this.starterSelectContainer.add(this.pokemonAbilityLabelText); - this.pokemonAbilityText = addTextObject(this.scene, 31, 127, '', TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + this.pokemonAbilityText = addTextObject(this.scene, starterInfoXPosition, 127, '', TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonAbilityText.setOrigin(0, 0); this.starterSelectContainer.add(this.pokemonAbilityText); - this.pokemonPassiveLabelText = addTextObject(this.scene, 6, 136, i18next.t("starterSelectUiHandler:passive"), TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + this.pokemonPassiveLabelText = addTextObject(this.scene, 6, 136, i18next.t("starterSelectUiHandler:passive"), TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonPassiveLabelText.setOrigin(0, 0); this.pokemonPassiveLabelText.setVisible(false); this.starterSelectContainer.add(this.pokemonPassiveLabelText); - this.pokemonPassiveText = addTextObject(this.scene, 31, 136, '', TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + this.pokemonPassiveText = addTextObject(this.scene, starterInfoXPosition, 136, '', TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonPassiveText.setOrigin(0, 0); this.starterSelectContainer.add(this.pokemonPassiveText); - this.pokemonNatureLabelText = addTextObject(this.scene, 6, 145, i18next.t("starterSelectUiHandler:nature"), TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + this.pokemonNatureLabelText = addTextObject(this.scene, 6, 145, i18next.t("starterSelectUiHandler:nature"), TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonNatureLabelText.setOrigin(0, 0); this.pokemonNatureLabelText.setVisible(false); this.starterSelectContainer.add(this.pokemonNatureLabelText); - this.pokemonNatureText = addBBCodeTextObject(this.scene, 31, 145, '', TextStyle.SUMMARY_ALT, { fontSize: '56px' }); + this.pokemonNatureText = addBBCodeTextObject(this.scene, starterInfoXPosition, 145, '', TextStyle.SUMMARY_ALT, { fontSize: starterInfoTextSize }); this.pokemonNatureText.setOrigin(0, 0); this.starterSelectContainer.add(this.pokemonNatureText); @@ -556,8 +580,11 @@ export default class StarterSelectUiHandler extends MessageUiHandler { let instructionTextSize = '42px'; // The font size should be set per language - const currentLanguage = i18next.language; + // currentLanguage is already defined in the previous code block switch (currentLanguage) { + case 'de': + instructionTextSize = '35px'; + break; case 'en': instructionTextSize = '42px'; break; @@ -567,12 +594,12 @@ export default class StarterSelectUiHandler extends MessageUiHandler { case 'fr': instructionTextSize = '42px'; break; - case 'de': - instructionTextSize = '35px'; - break; case 'it': instructionTextSize = '38px'; break; + case 'pt_BR': + instructionTextSize = '38px'; + break; case 'zh_CN': instructionTextSize = '42px'; break; From 38e3022d06f930c7abb530f87dae9b0530455297 Mon Sep 17 00:00:00 2001 From: Tempoanon <163687446+TempsRay@users.noreply.github.com> Date: Wed, 15 May 2024 11:32:10 -0400 Subject: [PATCH 11/46] Add missing biomes for camoflauge (#912) --- src/field/arena.ts | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/field/arena.ts b/src/field/arena.ts index a2bde94229d..75cc86fcebc 100644 --- a/src/field/arena.ts +++ b/src/field/arena.ts @@ -206,6 +206,7 @@ export class Arena { case Biome.TALL_GRASS: return Type.GRASS; case Biome.FOREST: + case Biome.JUNGLE: return Type.BUG; case Biome.SLUM: case Biome.SWAMP: @@ -237,8 +238,10 @@ export class Arena { 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: @@ -248,6 +251,8 @@ export class Arena { return Type.DRAGON; case Biome.ABYSS: return Type.DARK; + default: + return Type.UNKNOWN; } } From ac2e78129e490f20fa8f037d88ff52df029a397b Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 11:42:18 -0400 Subject: [PATCH 12/46] Add Save and Quit option to replace Return to Title --- src/locales/de/menu-ui-handler.ts | 2 +- src/locales/en/menu-ui-handler.ts | 2 +- src/locales/es/menu-ui-handler.ts | 2 +- src/locales/fr/menu-ui-handler.ts | 2 +- src/locales/it/menu-ui-handler.ts | 2 +- src/locales/pt_BR/menu-ui-handler.ts | 2 +- src/locales/zh_CN/menu-ui-handler.ts | 2 +- src/system/game-data.ts | 7 +++++-- src/ui/menu-ui-handler.ts | 19 +++++++++++-------- 9 files changed, 23 insertions(+), 17 deletions(-) diff --git a/src/locales/de/menu-ui-handler.ts b/src/locales/de/menu-ui-handler.ts index e330b726998..0197598cb81 100644 --- a/src/locales/de/menu-ui-handler.ts +++ b/src/locales/de/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Eier-Gacha", "MANAGE_DATA": "Daten verwalten", "COMMUNITY": "Community", - "RETURN_TO_TITLE": "Zurück zum Titelbildschirm", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Ausloggen", "slot": "Slot {{slotNumber}}", "importSession": "Sitzung importieren", diff --git a/src/locales/en/menu-ui-handler.ts b/src/locales/en/menu-ui-handler.ts index 5fde37ae360..eb8e474ee60 100644 --- a/src/locales/en/menu-ui-handler.ts +++ b/src/locales/en/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Egg Gacha", "MANAGE_DATA": "Manage Data", "COMMUNITY": "Community", - "RETURN_TO_TITLE": "Return To Title", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Log Out", "slot": "Slot {{slotNumber}}", "importSession": "Import Session", diff --git a/src/locales/es/menu-ui-handler.ts b/src/locales/es/menu-ui-handler.ts index ba7ea78fd8f..ebb76de6f77 100644 --- a/src/locales/es/menu-ui-handler.ts +++ b/src/locales/es/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha de Huevos", "MANAGE_DATA": "Gestionar Datos", "COMMUNITY": "Comunidad", - "RETURN_TO_TITLE": "Volver al Título", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Cerrar Sesión", "slot": "Ranura {{slotNumber}}", "importSession": "Importar Sesión", diff --git a/src/locales/fr/menu-ui-handler.ts b/src/locales/fr/menu-ui-handler.ts index 54328a05eb1..3233ec09e87 100644 --- a/src/locales/fr/menu-ui-handler.ts +++ b/src/locales/fr/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha-Œufs", "MANAGE_DATA": "Mes données", "COMMUNITY": "Communauté", - "RETURN_TO_TITLE": "Écran titre", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Déconnexion", "slot": "Emplacement {{slotNumber}}", "importSession": "Importer session", diff --git a/src/locales/it/menu-ui-handler.ts b/src/locales/it/menu-ui-handler.ts index 9def62d8da3..3e4362e76cf 100644 --- a/src/locales/it/menu-ui-handler.ts +++ b/src/locales/it/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha Uova", "MANAGE_DATA": "Gestisci Dati", "COMMUNITY": "Community", - "RETURN_TO_TITLE": "Ritorna al Titolo", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Disconnettiti", "slot": "Slot {{slotNumber}}", "importSession": "Importa Sessione", diff --git a/src/locales/pt_BR/menu-ui-handler.ts b/src/locales/pt_BR/menu-ui-handler.ts index 2e4d798cf65..bfe863e38ce 100644 --- a/src/locales/pt_BR/menu-ui-handler.ts +++ b/src/locales/pt_BR/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha de Ovos", "MANAGE_DATA": "Gerenciar Dados", "COMMUNITY": "Comunidade", - "RETURN_TO_TITLE": "Voltar ao Início", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "Logout", "slot": "Slot {{slotNumber}}", "importSession": "Importar Sessão", diff --git a/src/locales/zh_CN/menu-ui-handler.ts b/src/locales/zh_CN/menu-ui-handler.ts index 0405b3ececc..a4d343f6da7 100644 --- a/src/locales/zh_CN/menu-ui-handler.ts +++ b/src/locales/zh_CN/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "扭蛋机", "MANAGE_DATA": "管理数据", "COMMUNITY": "社区", - "RETURN_TO_TITLE": "返回标题画面", + "SAVE_AND_QUIT": "Save and Quit", "LOG_OUT": "登出", "slot": "存档位 {{slotNumber}}", "importSession": "导入存档", diff --git a/src/system/game-data.ts b/src/system/game-data.ts index c635d66c1f1..2691e79be61 100644 --- a/src/system/game-data.ts +++ b/src/system/game-data.ts @@ -358,12 +358,15 @@ export class GameData { if (cachedSystemData.timestamp > systemData.timestamp) { console.debug('Use cached system'); systemData = cachedSystemData; + systemDataStr = cachedSystemDataStr; } else this.clearLocalData(); } console.debug(systemData); + localStorage.setItem(`data_${loggedInUser.username}`, encrypt(systemDataStr, bypassLogin)); + /*const versions = [ this.scene.game.config.gameVersion, data.gameVersion || '0.0.0' ]; if (versions[0] !== versions[1]) { @@ -876,7 +879,7 @@ export class GameData { }) as SessionSaveData; } - saveAll(scene: BattleScene, skipVerification: boolean = false, sync: boolean = false, useCachedSession: boolean = false): Promise { + saveAll(scene: BattleScene, skipVerification: boolean = false, sync: boolean = false, useCachedSession: boolean = false, useCachedSystem: boolean = false): Promise { return new Promise(resolve => { Utils.executeIf(!skipVerification, updateUserInfo).then(success => { if (success !== null && !success) @@ -886,7 +889,7 @@ export class GameData { const sessionData = useCachedSession ? this.parseSessionData(decrypt(localStorage.getItem(`sessionData${scene.sessionSlotId ? scene.sessionSlotId : ''}_${loggedInUser.username}`), bypassLogin)) : this.getSessionSaveData(scene); const maxIntAttrValue = Math.pow(2, 31); - const systemData = this.getSystemSaveData(); + const systemData = useCachedSystem ? this.parseSystemData(decrypt(localStorage.getItem(`data_${loggedInUser.username}`), bypassLogin)) : this.getSystemSaveData(); const request = { system: systemData, diff --git a/src/ui/menu-ui-handler.ts b/src/ui/menu-ui-handler.ts index bf032667610..fb253d94f9b 100644 --- a/src/ui/menu-ui-handler.ts +++ b/src/ui/menu-ui-handler.ts @@ -20,7 +20,7 @@ export enum MenuOptions { EGG_GACHA, MANAGE_DATA, COMMUNITY, - RETURN_TO_TITLE, + SAVE_AND_QUIT, LOG_OUT } @@ -297,15 +297,18 @@ export default class MenuUiHandler extends MessageUiHandler { ui.setOverlayMode(Mode.MENU_OPTION_SELECT, this.communityConfig); success = true; break; - case MenuOptions.RETURN_TO_TITLE: + case MenuOptions.SAVE_AND_QUIT: if (this.scene.currentBattle) { success = true; - ui.showText(i18next.t("menuUiHandler:losingProgressionWarning"), null, () => { - ui.setOverlayMode(Mode.CONFIRM, () => this.scene.reset(true), () => { - ui.revertMode(); - ui.showText(null, 0); - }, false, -98); - }); + if (this.scene.currentBattle.turn > 1) { + ui.showText(i18next.t("menuUiHandler:losingProgressionWarning"), null, () => { + ui.setOverlayMode(Mode.CONFIRM, () => this.scene.gameData.saveAll(this.scene, true, true, true, true).then(() => this.scene.reset(true)), () => { + ui.revertMode(); + ui.showText(null, 0); + }, false, -98); + }); + } else + this.scene.gameData.saveAll(this.scene, true, true, true, true).then(() => this.scene.reset(true)); } else error = true; break; From fcffa000c5285beb2b31199cdfc3c64612771602 Mon Sep 17 00:00:00 2001 From: Lugiad Date: Wed, 15 May 2024 17:45:15 +0200 Subject: [PATCH 13/46] French translation Save and Quit --- src/locales/fr/menu-ui-handler.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/locales/fr/menu-ui-handler.ts b/src/locales/fr/menu-ui-handler.ts index 3233ec09e87..20e66754667 100644 --- a/src/locales/fr/menu-ui-handler.ts +++ b/src/locales/fr/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha-Œufs", "MANAGE_DATA": "Mes données", "COMMUNITY": "Communauté", - "SAVE_AND_QUIT": "Save and Quit", + "SAVE_AND_QUIT": "Sauver & quitter", "LOG_OUT": "Déconnexion", "slot": "Emplacement {{slotNumber}}", "importSession": "Importer session", From 9197f9f070370cf06134106aed5a5fedf3fb0d17 Mon Sep 17 00:00:00 2001 From: Xavion3 Date: Tue, 14 May 2024 07:26:32 +1000 Subject: [PATCH 14/46] Limit rare eggs to e4+ and fix trainer boss check Also fixes weighting to account for adjusted level ranges --- src/data/trainer-config.ts | 12 +++++++++--- src/field/pokemon.ts | 10 ++++++++-- 2 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src/data/trainer-config.ts b/src/data/trainer-config.ts index 36d76edcfab..5284773e4b6 100644 --- a/src/data/trainer-config.ts +++ b/src/data/trainer-config.ts @@ -855,14 +855,20 @@ export const trainerConfigs: TrainerConfigs = { }), [TrainerType.RIVAL_6]: new TrainerConfig(++t).setName('Finn').setHasGenders('Ivy').setHasCharSprite().setTitle('Rival').setBoss().setStaticParty().setMoneyMultiplier(3).setEncounterBgm('final').setBattleBgm('battle_rival_3').setPartyTemplates(trainerPartyTemplates.RIVAL_6) .setPartyMemberFunc(0, getRandomPartyMemberFunc([ Species.VENUSAUR, Species.CHARIZARD, Species.BLASTOISE, Species.MEGANIUM, Species.TYPHLOSION, Species.FERALIGATR, Species.SCEPTILE, Species.BLAZIKEN, Species.SWAMPERT, Species.TORTERRA, Species.INFERNAPE, Species.EMPOLEON, Species.SERPERIOR, Species.EMBOAR, Species.SAMUROTT, Species.CHESNAUGHT, Species.DELPHOX, Species.GRENINJA, Species.DECIDUEYE, Species.INCINEROAR, Species.PRIMARINA, Species.RILLABOOM, Species.CINDERACE, Species.INTELEON, Species.MEOWSCARADA, Species.SKELEDIRGE, Species.QUAQUAVAL ], TrainerSlot.TRAINER, true, - p => p.setBoss(true, 3)) - ) + p => { + p.setBoss(true, 3); + p.generateAndPopulateMoveset(); + })) .setPartyMemberFunc(1, getRandomPartyMemberFunc([ Species.PIDGEOT, Species.NOCTOWL, Species.SWELLOW, Species.STARAPTOR, Species.UNFEZANT, Species.TALONFLAME, Species.TOUCANNON, Species.CORVIKNIGHT, Species.KILOWATTREL ], TrainerSlot.TRAINER, true, - p => p.setBoss(true, 2))) + p => { + p.setBoss(true, 2); + p.generateAndPopulateMoveset(); + })) .setPartyMemberFunc(2, getSpeciesFilterRandomPartyMemberFunc((species: PokemonSpecies) => !pokemonEvolutions.hasOwnProperty(species.speciesId) && !pokemonPrevolutions.hasOwnProperty(species.speciesId) && species.baseTotal >= 450)) .setSpeciesFilter(species => species.baseTotal >= 540) .setPartyMemberFunc(5, getRandomPartyMemberFunc([ Species.RAYQUAZA ], TrainerSlot.TRAINER, true, p => { p.setBoss(); + p.generateAndPopulateMoveset(); p.pokeball = PokeballType.MASTER_BALL; p.shiny = true; p.variant = 1; diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index 48287cf39cb..eb08af3da55 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -1229,14 +1229,20 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container { for (let i = 0; i < 3; i++) { const moveId = speciesEggMoves[this.species.getRootSpeciesId()][i]; if (!movePool.some(m => m[0] === moveId) && !allMoves[moveId].name.endsWith(' (N)')) - movePool.push([moveId, Math.min(this.level * 0.5, 40)]); + movePool.push([moveId, 40]); } + const moveId = speciesEggMoves[this.species.getRootSpeciesId()][3]; + if (this.level >= 170 && !movePool.some(m => m[0] === moveId) && !allMoves[moveId].name.endsWith(' (N)') && !this.isBoss()) // No rare egg moves before e4 + movePool.push([moveId, 30]); if (this.fusionSpecies) { for (let i = 0; i < 3; i++) { const moveId = speciesEggMoves[this.fusionSpecies.getRootSpeciesId()][i]; if (!movePool.some(m => m[0] === moveId) && !allMoves[moveId].name.endsWith(' (N)')) - movePool.push([moveId, Math.min(this.level * 0.5, 30)]); + movePool.push([moveId, 40]); } + const moveId = speciesEggMoves[this.fusionSpecies.getRootSpeciesId()][3]; + if (this.level >= 170 && !movePool.some(m => m[0] === moveId) && !allMoves[moveId].name.endsWith(' (N)') && !this.isBoss()) // No rare egg moves before e4 + movePool.push([moveId, 30]); } } } From afcffab90f26509731e91ccf2f8ca8be991ba17b Mon Sep 17 00:00:00 2001 From: Lugiad Date: Wed, 15 May 2024 17:57:48 +0200 Subject: [PATCH 15/46] Added Gen names localizations in Starter Selection UI (+"Uncaught" translation in French) (#907) * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Update starter-select-ui-handler.ts * Update starter-select-ui-handler.ts * Added Gen names localizations in Starter Selection UI * Added Gen names localizations in Starter Selection UI * Updated with recent pt BR edits --- src/locales/de/starter-select-ui-handler.ts | 11 ++++++- src/locales/en/starter-select-ui-handler.ts | 11 ++++++- src/locales/es/starter-select-ui-handler.ts | 11 ++++++- src/locales/fr/starter-select-ui-handler.ts | 11 ++++++- src/locales/it/starter-select-ui-handler.ts | 9 ++++++ .../pt_BR/starter-select-ui-handler.ts | 11 ++++++- .../zh_CN/starter-select-ui-handler.ts | 11 ++++++- src/ui/starter-select-ui-handler.ts | 30 +++++++++++++------ 8 files changed, 90 insertions(+), 15 deletions(-) diff --git a/src/locales/de/starter-select-ui-handler.ts b/src/locales/de/starter-select-ui-handler.ts index 2e733c1a0ed..5f6dae32cf6 100644 --- a/src/locales/de/starter-select-ui-handler.ts +++ b/src/locales/de/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam": "Mit diesen Pokémon losziehen?", + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "Wachstum:", "ability": "Fhgkeit:", "passive": "Passiv:", @@ -32,4 +41,4 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "locked": "Gesperrt", "disabled": "Deaktiviert", "uncaught": "Uncaught" -} \ No newline at end of file +} diff --git a/src/locales/en/starter-select-ui-handler.ts b/src/locales/en/starter-select-ui-handler.ts index 2acceab69ff..19f8649dcc3 100644 --- a/src/locales/en/starter-select-ui-handler.ts +++ b/src/locales/en/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam":'Begin with these Pokémon?', + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "Growth Rate:", "ability": "Ability:", "passive": "Passive:", @@ -32,4 +41,4 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "locked": "Locked", "disabled": "Disabled", "uncaught": "Uncaught" -} \ No newline at end of file +} diff --git a/src/locales/es/starter-select-ui-handler.ts b/src/locales/es/starter-select-ui-handler.ts index 9b037209819..79bf6f9476e 100644 --- a/src/locales/es/starter-select-ui-handler.ts +++ b/src/locales/es/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam":'¿Comenzar con estos Pokémon?', + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "Crecimiento:", "ability": "Habilid:", "passive": "Pasiva:", @@ -32,4 +41,4 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "locked": "Locked", "disabled": "Disabled", "uncaught": "Uncaught" -} \ No newline at end of file +} diff --git a/src/locales/fr/starter-select-ui-handler.ts b/src/locales/fr/starter-select-ui-handler.ts index d26fa3314b6..380f4e9fd56 100644 --- a/src/locales/fr/starter-select-ui-handler.ts +++ b/src/locales/fr/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam":'Commencer avec ces Pokémon ?', + "gen1": "1G", + "gen2": "2G", + "gen3": "3G", + "gen4": "4G", + "gen5": "5G", + "gen6": "6G", + "gen7": "7G", + "gen8": "8G", + "gen9": "9G", "growthRate": "Croissance :", "ability": "Talent :", "passive": "Passif :", @@ -31,5 +40,5 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "disablePassive": "Désactiver Passif", "locked": "Verrouillé", "disabled": "Désactivé", - "uncaught": "Uncaught" + "uncaught": "Non-capturé" } diff --git a/src/locales/it/starter-select-ui-handler.ts b/src/locales/it/starter-select-ui-handler.ts index af95fc374bf..f2b44c37297 100644 --- a/src/locales/it/starter-select-ui-handler.ts +++ b/src/locales/it/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam":'Vuoi iniziare con questi Pokémon?', + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "Vel. Crescita:", "ability": "Abilità:", "passive": "Passiva:", diff --git a/src/locales/pt_BR/starter-select-ui-handler.ts b/src/locales/pt_BR/starter-select-ui-handler.ts index 4e0f5ca73f9..7d77f48f290 100644 --- a/src/locales/pt_BR/starter-select-ui-handler.ts +++ b/src/locales/pt_BR/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam": 'Começar com esses Pokémon?', + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "Crescimento:", "ability": "Habilidade:", "passive": "Passiva:", @@ -32,4 +41,4 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "locked": "Bloqueada", "disabled": "Desativada", "uncaught": "Não capturado" -} \ No newline at end of file +} diff --git a/src/locales/zh_CN/starter-select-ui-handler.ts b/src/locales/zh_CN/starter-select-ui-handler.ts index ace02c1c227..99ecc31afbb 100644 --- a/src/locales/zh_CN/starter-select-ui-handler.ts +++ b/src/locales/zh_CN/starter-select-ui-handler.ts @@ -7,6 +7,15 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const starterSelectUiHandler: SimpleTranslationEntries = { "confirmStartTeam":'使用这些宝可梦开始游戏吗?', + "gen1": "I", + "gen2": "II", + "gen3": "III", + "gen4": "IV", + "gen5": "V", + "gen6": "VI", + "gen7": "VII", + "gen8": "VIII", + "gen9": "IX", "growthRate": "成长速度:", "ability": "特性:", "passive": "被动:", @@ -32,4 +41,4 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "locked": "Locked", "disabled": "Disabled", "uncaught": "Uncaught" -} \ No newline at end of file +} diff --git a/src/ui/starter-select-ui-handler.ts b/src/ui/starter-select-ui-handler.ts index 6017438e013..a20f3a3647f 100644 --- a/src/ui/starter-select-ui-handler.ts +++ b/src/ui/starter-select-ui-handler.ts @@ -86,7 +86,17 @@ function getValueReductionCandyCounts(baseValue: integer): [integer, integer] { } } -const gens = [ 'I', 'II', 'III', 'IV', 'V', 'VI', 'VII', 'VIII', 'IX' ]; +const gens = [ + i18next.t("starterSelectUiHandler:gen1"), + i18next.t("starterSelectUiHandler:gen2"), + i18next.t("starterSelectUiHandler:gen3"), + i18next.t("starterSelectUiHandler:gen4"), + i18next.t("starterSelectUiHandler:gen5"), + i18next.t("starterSelectUiHandler:gen6"), + i18next.t("starterSelectUiHandler:gen7"), + i18next.t("starterSelectUiHandler:gen8"), + i18next.t("starterSelectUiHandler:gen9") +]; export default class StarterSelectUiHandler extends MessageUiHandler { private starterSelectContainer: Phaser.GameObjects.Container; @@ -1287,15 +1297,17 @@ export default class StarterSelectUiHandler extends MessageUiHandler { updateGenOptions(): void { let text = ''; for (let g = this.genScrollCursor; g <= this.genScrollCursor + 2; g++) { - let optionText = gens[g]; - if (g === this.genScrollCursor && this.genScrollCursor) - optionText = '↑'; - else if (g === this.genScrollCursor + 2 && this.genScrollCursor < gens.length - 3) - optionText = '↓' - text += `${text ? '\n' : ''}${optionText}`; + let optionText = ''; + if (g === this.genScrollCursor && this.genScrollCursor) + optionText = '↑'; + else if (g === this.genScrollCursor + 2 && this.genScrollCursor < gens.length - 3) + optionText = '↓' + else + optionText = i18next.t(`starterSelectUiHandler:gen${g + 1}`); + text += `${text ? '\n' : ''}${optionText}`; } this.genOptionsText.setText(text); - } +} setGenMode(genMode: boolean): boolean { this.genCursorObj.setVisible(genMode && !this.startCursorObj.visible); @@ -1860,4 +1872,4 @@ export default class StarterSelectUiHandler extends MessageUiHandler { icon.setFrame(species.getIconId(female, formIndex, false, variant)); } } -} \ No newline at end of file +} From 7769c06393d5a0f96002e31d438ad640ee58e720 Mon Sep 17 00:00:00 2001 From: Adrian Torrano <68144167+torranx@users.noreply.github.com> Date: Thu, 16 May 2024 00:01:20 +0800 Subject: [PATCH 16/46] add logic to conditionally align window (#851) --- src/system/settings.ts | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/system/settings.ts b/src/system/settings.ts index 15c1f19aa04..91d6459e408 100644 --- a/src/system/settings.ts +++ b/src/system/settings.ts @@ -2,7 +2,7 @@ import SettingsUiHandler from "#app/ui/settings-ui-handler"; import { Mode } from "#app/ui/ui"; import i18next from "i18next"; import BattleScene from "../battle-scene"; -import { hasTouchscreen } from "../touch-controls"; +import { hasTouchscreen, isMobile } from "../touch-controls"; import { updateWindowType } from "../ui/ui-theme"; import { PlayerGender } from "./game-data"; @@ -167,6 +167,14 @@ export function setSetting(scene: BattleScene, setting: Setting, value: integer) const touchControls = document.getElementById('touchControls'); if (touchControls) touchControls.classList.toggle('visible', scene.enableTouchControls); + + const isLandscape = window.matchMedia("(orientation: landscape)").matches; + const appContainer = document.getElementById('app'); + + if (!isMobile() && isLandscape && !scene.enableTouchControls) + appContainer.style.alignItems = 'center'; + else + appContainer.style.alignItems = 'start'; break; case Setting.Vibration: scene.enableVibration = settingOptions[setting][value] !== 'Disabled' && hasTouchscreen(); From 78f79653049baff0ec6514b743e5f602d43ad391 Mon Sep 17 00:00:00 2001 From: Flashfyre Date: Wed, 15 May 2024 12:22:32 -0400 Subject: [PATCH 17/46] Revert "add logic to conditionally align window (#851)" This reverts commit 7769c06393d5a0f96002e31d438ad640ee58e720. --- src/system/settings.ts | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/src/system/settings.ts b/src/system/settings.ts index 91d6459e408..15c1f19aa04 100644 --- a/src/system/settings.ts +++ b/src/system/settings.ts @@ -2,7 +2,7 @@ import SettingsUiHandler from "#app/ui/settings-ui-handler"; import { Mode } from "#app/ui/ui"; import i18next from "i18next"; import BattleScene from "../battle-scene"; -import { hasTouchscreen, isMobile } from "../touch-controls"; +import { hasTouchscreen } from "../touch-controls"; import { updateWindowType } from "../ui/ui-theme"; import { PlayerGender } from "./game-data"; @@ -167,14 +167,6 @@ export function setSetting(scene: BattleScene, setting: Setting, value: integer) const touchControls = document.getElementById('touchControls'); if (touchControls) touchControls.classList.toggle('visible', scene.enableTouchControls); - - const isLandscape = window.matchMedia("(orientation: landscape)").matches; - const appContainer = document.getElementById('app'); - - if (!isMobile() && isLandscape && !scene.enableTouchControls) - appContainer.style.alignItems = 'center'; - else - appContainer.style.alignItems = 'start'; break; case Setting.Vibration: scene.enableVibration = settingOptions[setting][value] !== 'Disabled' && hasTouchscreen(); From 44c0d29c1d7b070f61ed9961e556f25c8dd78ff9 Mon Sep 17 00:00:00 2001 From: Adrian Torrano <68144167+torranx@users.noreply.github.com> Date: Thu, 16 May 2024 00:42:34 +0800 Subject: [PATCH 18/46] Add missing translation for learning move (#879) * add missing translation for learn move * fix countdown german translation * Fix countdown French translation --------- Co-authored-by: Lugiad --- src/locales/de/battle.ts | 2 ++ src/locales/en/battle.ts | 2 ++ src/locales/es/battle.ts | 2 ++ src/locales/fr/battle.ts | 2 ++ src/locales/it/battle.ts | 2 ++ src/locales/pt_BR/battle.ts | 2 ++ src/locales/zh_CN/battle.ts | 2 ++ src/phases.ts | 4 ++-- 8 files changed, 16 insertions(+), 2 deletions(-) diff --git a/src/locales/de/battle.ts b/src/locales/de/battle.ts index 1dc7b68fd7d..e0aa20b6c94 100644 --- a/src/locales/de/battle.ts +++ b/src/locales/de/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} hat\n{{moveName}} nicht erlernt.", "learnMoveForgetQuestion": "Welche Attacke soll vergessen werden?", "learnMoveForgetSuccess": "{{pokemonName}} hat\n{{moveName}} vergessen.", + "countdownPoof": "@d{32}Eins, @d{15}zwei @d{15}und@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}schwupp!", + "learnMoveAnd": "Und…", "levelCapUp": "Das Levellimit\nhat sich zu {{levelCap}} erhöht!", "moveNotImplemented": "{{moveName}} ist noch nicht implementiert und kann nicht ausgewählt werden.", "moveNoPP": "Es sind keine AP für\ndiese Attacke mehr übrig!", diff --git a/src/locales/en/battle.ts b/src/locales/en/battle.ts index 7c948e6f09f..0162f2922af 100644 --- a/src/locales/en/battle.ts +++ b/src/locales/en/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} did not learn the\nmove {{moveName}}.", "learnMoveForgetQuestion": "Which move should be forgotten?", "learnMoveForgetSuccess": "{{pokemonName}} forgot how to\nuse {{moveName}}.", + "countdownPoof": "@d{32}1, @d{15}2, and@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}Poof!", + "learnMoveAnd": "And…", "levelCapUp": "The level cap\nhas increased to {{levelCap}}!", "moveNotImplemented": "{{moveName}} is not yet implemented and cannot be selected.", "moveNoPP": "There's no PP left for\nthis move!", diff --git a/src/locales/es/battle.ts b/src/locales/es/battle.ts index 6fdcf4fbc86..76a73142ad6 100644 --- a/src/locales/es/battle.ts +++ b/src/locales/es/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} no ha aprendido {{moveName}}.", "learnMoveForgetQuestion": "¿Qué movimiento quieres que olvide?", "learnMoveForgetSuccess": "{{pokemonName}} ha olvidado cómo utilizar {{moveName}}.", + "countdownPoof": "@d{32}1, @d{15}2, @d{15}y@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}¡Puf!", + "learnMoveAnd": "Y…", "levelCapUp": "¡Se ha incrementado el\nnivel máximo a {{levelCap}}!", "moveNotImplemented": "{{moveName}} aún no está implementado y no se puede seleccionar.", "moveNoPP": "There's no PP left for\nthis move!", diff --git a/src/locales/fr/battle.ts b/src/locales/fr/battle.ts index e34902b8cb1..a76cc9cdeaf 100644 --- a/src/locales/fr/battle.ts +++ b/src/locales/fr/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} n’a pas appris\n{{moveName}}.", "learnMoveForgetQuestion": "Quelle capacité doit être oubliée ?", "learnMoveForgetSuccess": "{{pokemonName}} oublie comment\nutiliser {{moveName}}.", + "countdownPoof": "@d{32}1, @d{15}2, @d{15}et@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}Tadaaa !", + "learnMoveAnd": "Et…", "levelCapUp": "La limite de niveau\na été augmentée à {{levelCap}} !", "moveNotImplemented": "{{moveName}} n’est pas encore implémenté et ne peut pas être sélectionné.", "moveNoPP": "Il n’y a plus de PP pour\ncette capacité !", diff --git a/src/locales/it/battle.ts b/src/locales/it/battle.ts index a3cffaa60d7..702ec0708ef 100644 --- a/src/locales/it/battle.ts +++ b/src/locales/it/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} non ha imparato\n{{moveName}}.", "learnMoveForgetQuestion": "Quale mossa deve dimenticare?", "learnMoveForgetSuccess": "{{pokemonName}} ha dimenticato la mossa\n{{moveName}}.", + "countdownPoof": "@d{32}1, @d{15}2, @d{15}e@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}Puff!", + "learnMoveAnd": "E…", "levelCapUp": "Il livello massimo\nè aumentato a {{levelCap}}!", "moveNotImplemented": "{{moveName}} non è ancora implementata e non può essere selezionata.", "moveNoPP": "Non ci sono PP rimanenti\nper questa mossa!", diff --git a/src/locales/pt_BR/battle.ts b/src/locales/pt_BR/battle.ts index ed579845cd7..39f889deeac 100644 --- a/src/locales/pt_BR/battle.ts +++ b/src/locales/pt_BR/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} não aprendeu {{moveName}}.", "learnMoveForgetQuestion": "Qual movimento quer esquecer?", "learnMoveForgetSuccess": "{{pokemonName}} esqueceu como usar {{moveName}}.", + "countdownPoof": "@d{32}1, @d{15}2, @d{15}e@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}Puf!", + "learnMoveAnd": "E…", "levelCapUp": "O nível máximo aumentou\npara {{levelCap}}!", "moveNotImplemented": "{{moveName}} ainda não foi implementado e não pode ser usado.", "moveNoPP": "Não há mais PP\npara esse movimento!", diff --git a/src/locales/zh_CN/battle.ts b/src/locales/zh_CN/battle.ts index 3a92b4f9f21..16efae75afd 100644 --- a/src/locales/zh_CN/battle.ts +++ b/src/locales/zh_CN/battle.ts @@ -31,6 +31,8 @@ export const battle: SimpleTranslationEntries = { "learnMoveNotLearned": "{{pokemonName}} 没有学会 {{moveName}}。", "learnMoveForgetQuestion": "要忘记哪个技能?", "learnMoveForgetSuccess": "{{pokemonName}} 忘记了\n如何使用 {{moveName}}。", + "countdownPoof": "@d{32}1, @d{15}2, @d{15}和@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}噗!", + "learnMoveAnd": "和…", "levelCapUp": "等级上限提升到 {{levelCap}}!", "moveNotImplemented": "{{moveName}} 尚未实装,无法选择。", "moveNoPP": "这个技能的 PP 用完了", diff --git a/src/phases.ts b/src/phases.ts index 88957ba1636..e2755328c69 100644 --- a/src/phases.ts +++ b/src/phases.ts @@ -3967,9 +3967,9 @@ export class LearnMovePhase extends PlayerPartyMemberPokemonPhase { return; } this.scene.ui.setMode(messageMode).then(() => { - this.scene.ui.showText('@d{32}1, @d{15}2, and@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}Poof!', null, () => { + this.scene.ui.showText(i18next.t('battle:countdownPoof'), null, () => { this.scene.ui.showText(i18next.t('battle:learnMoveForgetSuccess', { pokemonName: pokemon.name, moveName: pokemon.moveset[moveIndex].getName() }), null, () => { - this.scene.ui.showText('And…', null, () => { + this.scene.ui.showText(i18next.t('battle:learnMoveAnd'), null, () => { pokemon.setMove(moveIndex, Moves.NONE); this.scene.unshiftPhase(new LearnMovePhase(this.scene, this.partyMemberIndex, this.moveId)); this.end(); From b8dff030aadadf98e7e483ebe44c98708767ef8e Mon Sep 17 00:00:00 2001 From: Surinam <67292578+suriinam@users.noreply.github.com> Date: Wed, 15 May 2024 19:31:18 +0200 Subject: [PATCH 19/46] Weather & evolution i18n with french translations (#380) Co-authored-by: Marius MICHAUD --- src/data/weather.ts | 55 ++++++++++++++++++------------------ src/evolution-phase.ts | 11 ++++---- src/locales/de/menu.ts | 5 ++++ src/locales/de/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/en/config.ts | 4 ++- src/locales/en/menu.ts | 5 ++++ src/locales/en/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/es/config.ts | 4 ++- src/locales/es/menu.ts | 5 ++++ src/locales/es/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/fr/config.ts | 4 ++- src/locales/fr/menu.ts | 5 ++++ src/locales/fr/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/it/config.ts | 4 ++- src/locales/it/menu.ts | 5 ++++ src/locales/it/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/pt_BR/config.ts | 4 ++- src/locales/pt_BR/menu.ts | 5 ++++ src/locales/pt_BR/weather.ts | 44 +++++++++++++++++++++++++++++ src/locales/zh_CN/config.ts | 4 ++- src/locales/zh_CN/menu.ts | 5 ++++ src/locales/zh_CN/weather.ts | 44 +++++++++++++++++++++++++++++ src/plugins/i18n.ts | 1 + 23 files changed, 396 insertions(+), 38 deletions(-) create mode 100644 src/locales/de/weather.ts create mode 100644 src/locales/en/weather.ts create mode 100644 src/locales/es/weather.ts create mode 100644 src/locales/fr/weather.ts create mode 100644 src/locales/it/weather.ts create mode 100644 src/locales/pt_BR/weather.ts create mode 100644 src/locales/zh_CN/weather.ts diff --git a/src/data/weather.ts b/src/data/weather.ts index 1409920a1bc..eb30f22f36b 100644 --- a/src/data/weather.ts +++ b/src/data/weather.ts @@ -7,6 +7,7 @@ import * as Utils from "../utils"; import BattleScene from "../battle-scene"; import { SuppressWeatherEffectAbAttr } from "./ability"; import { TerrainType } from "./terrain"; +import i18next from "i18next"; export enum WeatherType { NONE, @@ -121,23 +122,23 @@ export class Weather { export function getWeatherStartMessage(weatherType: WeatherType): string { switch (weatherType) { case WeatherType.SUNNY: - return 'The sunlight got bright!'; + return i18next.t('weather:sunnyStartMessage'); case WeatherType.RAIN: - return 'A downpour started!'; + return i18next.t('weather:rainStartMessage'); case WeatherType.SANDSTORM: - return 'A sandstorm brewed!'; + return i18next.t('weather:sandstormStartMessage'); case WeatherType.HAIL: - return 'It started to hail!'; + return i18next.t('weather:hailStartMessage'); case WeatherType.SNOW: - return 'It started to snow!'; + return i18next.t('weather:snowStartMessage'); case WeatherType.FOG: - return 'A thick fog emerged!' + return i18next.t('weather:fogStartMessage'); case WeatherType.HEAVY_RAIN: - return 'A heavy downpour started!' + return i18next.t('weather:heavyRainStartMessage'); case WeatherType.HARSH_SUN: - return 'The sunlight got hot!' + return i18next.t('weather:harshSunStartMessage'); case WeatherType.STRONG_WINDS: - return 'A heavy wind began!'; + return i18next.t('weather:strongWindsStartMessage'); } return null; @@ -146,23 +147,23 @@ export function getWeatherStartMessage(weatherType: WeatherType): string { export function getWeatherLapseMessage(weatherType: WeatherType): string { switch (weatherType) { case WeatherType.SUNNY: - return 'The sunlight is strong.'; + return i18next.t('weather:sunnyLapseMessage'); case WeatherType.RAIN: - return 'The downpour continues.'; + return i18next.t('weather:rainLapseMessage'); case WeatherType.SANDSTORM: - return 'The sandstorm rages.'; + return i18next.t('weather:sandstormLapseMessage'); case WeatherType.HAIL: - return 'Hail continues to fall.'; + return i18next.t('weather:hailLapseMessage'); case WeatherType.SNOW: - return 'The snow is falling down.'; + return i18next.t('weather:snowLapseMessage'); case WeatherType.FOG: - return 'The fog continues.'; + return i18next.t('weather:fogLapseMessage'); case WeatherType.HEAVY_RAIN: - return 'The heavy downpour continues.' + return i18next.t('weather:heavyRainLapseMessage'); case WeatherType.HARSH_SUN: - return 'The sun is scorching hot.' + return i18next.t('weather:harshSunLapseMessage'); case WeatherType.STRONG_WINDS: - return 'The wind blows intensely.'; + return i18next.t('weather:strongWindsLapseMessage'); } return null; @@ -182,23 +183,23 @@ export function getWeatherDamageMessage(weatherType: WeatherType, pokemon: Pokem export function getWeatherClearMessage(weatherType: WeatherType): string { switch (weatherType) { case WeatherType.SUNNY: - return 'The sunlight faded.'; + return i18next.t('weather:sunnyClearMessage'); case WeatherType.RAIN: - return 'The rain stopped.'; + return i18next.t('weather:rainClearMessage'); case WeatherType.SANDSTORM: - return 'The sandstorm subsided.'; + return i18next.t('weather:sandstormClearMessage'); case WeatherType.HAIL: - return 'The hail stopped.'; + return i18next.t('weather:hailClearMessage'); case WeatherType.SNOW: - return 'The snow stopped.'; + return i18next.t('weather:snowClearMessage'); case WeatherType.FOG: - return 'The fog disappeared.' + return i18next.t('weather:fogClearMessage'); case WeatherType.HEAVY_RAIN: - return 'The heavy rain stopped.' + return i18next.t('weather:heavyRainClearMessage'); case WeatherType.HARSH_SUN: - return 'The harsh sunlight faded.' + return i18next.t('weather:harshSunClearMessage'); case WeatherType.STRONG_WINDS: - return 'The heavy wind stopped.'; + return i18next.t('weather:strongWindsClearMessage'); } return null; diff --git a/src/evolution-phase.ts b/src/evolution-phase.ts index fb3803a1e75..7684d7797a2 100644 --- a/src/evolution-phase.ts +++ b/src/evolution-phase.ts @@ -9,6 +9,7 @@ import { LearnMovePhase } from "./phases"; import { cos, sin } from "./field/anims"; import { PlayerPokemon } from "./field/pokemon"; import { getTypeRgb } from "./data/type"; +import i18next from "i18next"; export class EvolutionPhase extends Phase { protected pokemon: PlayerPokemon; @@ -115,7 +116,7 @@ export class EvolutionPhase extends Phase { const evolutionHandler = this.scene.ui.getHandler() as EvolutionSceneHandler; const preName = this.pokemon.name; - this.scene.ui.showText(`What?\n${preName} is evolving!`, null, () => { + this.scene.ui.showText(i18next.t('menu:evolving', { pokemonName: preName }), null, () => { this.pokemon.cry(); this.pokemon.getPossibleEvolution(this.evolution).then(evolvedPokemon => { @@ -187,8 +188,8 @@ export class EvolutionPhase extends Phase { this.scene.unshiftPhase(new EndEvolutionPhase(this.scene)); - this.scene.ui.showText(`${preName} stopped evolving.`, null, () => { - this.scene.ui.showText(`Would you like to pause evolutions for ${preName}?\nEvolutions can be re-enabled from the party screen.`, null, () => { + this.scene.ui.showText(i18next.t('menu:stoppedEvolving', { pokemonName: preName }), null, () => { + this.scene.ui.showText(i18next.t('menu:pauseEvolutionsQuestion', { pokemonName: preName }), null, () => { const end = () => { this.scene.ui.showText(null, 0); this.scene.playBgm(); @@ -198,7 +199,7 @@ export class EvolutionPhase extends Phase { this.scene.ui.setOverlayMode(Mode.CONFIRM, () => { this.scene.ui.revertMode(); this.pokemon.pauseEvolutions = true; - this.scene.ui.showText(`Evolutions have been paused for ${preName}.`, null, end, 3000); + this.scene.ui.showText(i18next.t('menu:evolutionsPaused', { pokemonName: preName }), null, end, 3000); }, () => { this.scene.ui.revertMode(); this.scene.time.delayedCall(3000, end); @@ -249,7 +250,7 @@ export class EvolutionPhase extends Phase { this.scene.playSoundWithoutBgm('evolution_fanfare'); evolvedPokemon.destroy(); - this.scene.ui.showText(`Congratulations!\nYour ${preName} evolved into ${this.pokemon.name}!`, null, () => this.end(), null, true, Utils.fixedInt(4000)); + this.scene.ui.showText(i18next.t('menu:evolutionDone', { pokemonName: preName, evolvedPokemonName: this.pokemon.name }), null, () => this.end(), null, true, Utils.fixedInt(4000)); this.scene.time.delayedCall(Utils.fixedInt(4250), () => this.scene.playBgm()); }); }); diff --git a/src/locales/de/menu.ts b/src/locales/de/menu.ts index c22b940a8eb..7d96f9130eb 100644 --- a/src/locales/de/menu.ts +++ b/src/locales/de/menu.ts @@ -35,6 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Bist du ein Junge oder ein Mädchen?", "boy": "Junge", "girl": "Mädchen", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "dailyRankings": "Tägliche Rangliste", "weeklyRankings": "Wöchentliche Rangliste", "noRankings": "Keine Rangliste", diff --git a/src/locales/de/weather.ts b/src/locales/de/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/de/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/locales/en/config.ts b/src/locales/en/config.ts index f5e8a68b09c..9259aa5cbe1 100644 --- a/src/locales/en/config.ts +++ b/src/locales/en/config.ts @@ -13,6 +13,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { weather } from "./weather"; export const enConfig = { @@ -30,5 +31,6 @@ export const enConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + weather: weather } \ No newline at end of file diff --git a/src/locales/en/menu.ts b/src/locales/en/menu.ts index 7a5043a98e2..7db9ea3aa6a 100644 --- a/src/locales/en/menu.ts +++ b/src/locales/en/menu.ts @@ -35,6 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Are you a boy or a girl?", "boy": "Boy", "girl": "Girl", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "dailyRankings": "Daily Rankings", "weeklyRankings": "Weekly Rankings", "noRankings": "No Rankings", diff --git a/src/locales/en/weather.ts b/src/locales/en/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/en/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/locales/es/config.ts b/src/locales/es/config.ts index c56a8d384c2..f6d6f2715d9 100644 --- a/src/locales/es/config.ts +++ b/src/locales/es/config.ts @@ -13,6 +13,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { weather } from "./weather"; export const esConfig = { @@ -30,5 +31,6 @@ export const esConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + weather: weather } \ No newline at end of file diff --git a/src/locales/es/menu.ts b/src/locales/es/menu.ts index 4839630bc56..6a7f2587a0f 100644 --- a/src/locales/es/menu.ts +++ b/src/locales/es/menu.ts @@ -35,6 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "¿Eres un chico o una chica?", "boy": "Chico", "girl": "Chica", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "dailyRankings": "Rankings Diarios", "weeklyRankings": "Rankings Semanales", "noRankings": "Sin Rankings", diff --git a/src/locales/es/weather.ts b/src/locales/es/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/es/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/locales/fr/config.ts b/src/locales/fr/config.ts index 89669aceb73..4179c758ff9 100644 --- a/src/locales/fr/config.ts +++ b/src/locales/fr/config.ts @@ -13,6 +13,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { weather } from "./weather"; export const frConfig = { @@ -30,5 +31,6 @@ export const frConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + weather: weather } \ No newline at end of file diff --git a/src/locales/fr/menu.ts b/src/locales/fr/menu.ts index 2723de58752..7cf277889df 100644 --- a/src/locales/fr/menu.ts +++ b/src/locales/fr/menu.ts @@ -30,6 +30,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Es-tu un garçon ou une fille ?", "boy": "Garçon", "girl": "Fille", + "evolving": "Hein ?\n{{pokemonName}} évolue !", + "stoppedEvolving": "{{pokemonName}} a stoppé son évolution.", + "pauseEvolutionsQuestion": "Voulez-vous pauser les évolutions pour {{pokemonName}} ?\nLes évolutions peuvent être réactivées depuis l'écran d'équipe.", + "evolutionsPaused": "Les évolutions ont été mises en pause pour {{pokemonName}}.", + "evolutionDone": "Félicitations !\nVotre {{pokemonName}} a évolué en {{evolvedPokemonName}} !", "dailyRankings": "Classement du Jour", "weeklyRankings": "Classement de la Semaine", "noRankings": "Pas de Classement", diff --git a/src/locales/fr/weather.ts b/src/locales/fr/weather.ts new file mode 100644 index 00000000000..75b12cf0114 --- /dev/null +++ b/src/locales/fr/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "Les rayons du soleil brillent !", + "sunnyLapseMessage": "Les rayons du soleil brillent fort.", + "sunnyClearMessage": "Les rayons du soleil se dissipent.", + + "rainStartMessage": "Il commence à pleuvoir !", + "rainLapseMessage": "La pluie continue.", + "rainClearMessage": "La pluie s'est arrêtée.", + + "sandstormStartMessage": "Une tempête de sable se prépare !", + "sandstormLapseMessage": "La tempête de sable fait rage.", + "sandstormClearMessage": "La tempête de sable se calme.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} subit les dégâts\nde la tempête de sable !", + + "hailStartMessage": "Il commence à grêler !", + "hailLapseMessage": "La grêle continue.", + "hailClearMessage": "La grêle s'est arrêtée.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} subit les dégâts\nde la grêle !", + + "snowStartMessage": "Il commence à neiger !", + "snowLapseMessage": "La neige continue de tomber.", + "snowClearMessage": "La neige s'est arrêtée.", + + "fogStartMessage": "Un brouillard épais émerge !", + "fogLapseMessage": "Le brouillard continue.", + "fogClearMessage": "Le brouillard a disparu.", + + "heavyRainStartMessage": "Une pluie battante s'abat soudainement !", + "heavyRainLapseMessage": "La pluie battante continue.", + "heavyRainClearMessage": "La pluie battante s'est arrêtée.", + + "harshSunStartMessage": "Les rayons du soleil s'intensifient !", + "harshSunLapseMessage": "Le soleil est brûlant.", + "harshSunClearMessage": "Le soleil brûlant se dissipe.", + + "strongWindsStartMessage": "Un vent violent se lève !", + "strongWindsLapseMessage": "Le vent souffle violemment.", + "strongWindsClearMessage": "Le vent violent s'est arrêté." +} \ No newline at end of file diff --git a/src/locales/it/config.ts b/src/locales/it/config.ts index 6ba9aa3affa..85e2e629184 100644 --- a/src/locales/it/config.ts +++ b/src/locales/it/config.ts @@ -13,6 +13,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { weather } from "./weather"; export const itConfig = { @@ -30,5 +31,6 @@ export const itConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + weather: weather } \ No newline at end of file diff --git a/src/locales/it/menu.ts b/src/locales/it/menu.ts index 1344b21cc53..ff41b8ab9dc 100644 --- a/src/locales/it/menu.ts +++ b/src/locales/it/menu.ts @@ -40,6 +40,11 @@ export const menu: SimpleTranslationEntries = { "noRankings": "Nessuna Classifica", "loading": "Caricamento…", "playersOnline": "Giocatori Online", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "empty":"Vuoto", "yes":"Si", "no":"No", diff --git a/src/locales/it/weather.ts b/src/locales/it/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/it/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/locales/pt_BR/config.ts b/src/locales/pt_BR/config.ts index fc58d45ce87..83d0641c8fa 100644 --- a/src/locales/pt_BR/config.ts +++ b/src/locales/pt_BR/config.ts @@ -12,6 +12,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { weather } from "./weather"; export const ptBrConfig = { @@ -28,5 +29,6 @@ export const ptBrConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + weather: weather } \ No newline at end of file diff --git a/src/locales/pt_BR/menu.ts b/src/locales/pt_BR/menu.ts index 474ac867efc..9cbde542037 100644 --- a/src/locales/pt_BR/menu.ts +++ b/src/locales/pt_BR/menu.ts @@ -35,6 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Você é um menino ou uma menina?", "boy": "Menino", "girl": "Menina", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "dailyRankings": "Classificação Diária", "weeklyRankings": "Classificação Semanal", "noRankings": "Sem Classificação", diff --git a/src/locales/pt_BR/weather.ts b/src/locales/pt_BR/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/pt_BR/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/locales/zh_CN/config.ts b/src/locales/zh_CN/config.ts index 496fd983c06..9a70eafb8e1 100644 --- a/src/locales/zh_CN/config.ts +++ b/src/locales/zh_CN/config.ts @@ -12,6 +12,7 @@ import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; import { nature } from "./nature"; +import { weather } from "./weather"; export const zhCnConfig = { @@ -29,5 +30,6 @@ export const zhCnConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, - nature: nature + nature: nature, + weather: weather } \ No newline at end of file diff --git a/src/locales/zh_CN/menu.ts b/src/locales/zh_CN/menu.ts index e9e12a6b328..1cbfa905758 100644 --- a/src/locales/zh_CN/menu.ts +++ b/src/locales/zh_CN/menu.ts @@ -35,6 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "你是男孩还是女孩?", "boy": "男孩", "girl": "女孩", + "evolving": "What?\n{{pokemonName}} is evolving!", + "stoppedEvolving": "{{pokemonName}} stopped evolving.", + "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", + "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", + "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", "dailyRankings": "每日排名", "weeklyRankings": "每周排名", "noRankings": "无排名", diff --git a/src/locales/zh_CN/weather.ts b/src/locales/zh_CN/weather.ts new file mode 100644 index 00000000000..999613f1566 --- /dev/null +++ b/src/locales/zh_CN/weather.ts @@ -0,0 +1,44 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +/** + * The weather namespace holds text displayed when weather is active during a battle + */ +export const weather: SimpleTranslationEntries = { + "sunnyStartMessage": "The sunlight got bright!", + "sunnyLapseMessage": "The sunlight is strong.", + "sunnyClearMessage": "The sunlight faded.", + + "rainStartMessage": "A downpour started!", + "rainLapseMessage": "The downpour continues.", + "rainClearMessage": "The rain stopped.", + + "sandstormStartMessage": "A sandstorm brewed!", + "sandstormLapseMessage": "The sandstorm rages.", + "sandstormClearMessage": "The sandstorm subsided.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + + "hailStartMessage": "It started to hail!", + "hailLapseMessage": "Hail continues to fall.", + "hailClearMessage": "The hail stopped.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + + "snowStartMessage": "It started to snow!", + "snowLapseMessage": "The snow is falling down.", + "snowClearMessage": "The snow stopped.", + + "fogStartMessage": "A thick fog emerged!", + "fogLapseMessage": "The fog continues.", + "fogClearMessage": "The fog disappeared.", + + "heavyRainStartMessage": "A heavy downpour started!", + "heavyRainLapseMessage": "The heavy downpour continues.", + "heavyRainClearMessage": "The heavy rain stopped.", + + "harshSunStartMessage": "The sunlight got hot!", + "harshSunLapseMessage": "The sun is scorching hot.", + "harshSunClearMessage": "The harsh sunlight faded.", + + "strongWindsStartMessage": "A heavy wind began!", + "strongWindsLapseMessage": "The wind blows intensely.", + "strongWindsClearMessage": "The heavy wind stopped." +} \ No newline at end of file diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index 82a5a51ba12..44712b12778 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -110,6 +110,7 @@ declare module 'i18next' { starterSelectUiHandler: SimpleTranslationEntries; nature: SimpleTranslationEntries; growth: SimpleTranslationEntries; + weather: SimpleTranslationEntries; }; } } From 2778eb2651a0a50abbda5a941b1abdc004e46a21 Mon Sep 17 00:00:00 2001 From: Lugiad Date: Wed, 15 May 2024 20:05:07 +0200 Subject: [PATCH 20/46] French weather.ts corrections (#923) * French weather.ts corrections * French weather.ts corrections --- src/locales/fr/weather.ts | 48 +++++++++++++++++++-------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/src/locales/fr/weather.ts b/src/locales/fr/weather.ts index 75b12cf0114..e73e51a53a2 100644 --- a/src/locales/fr/weather.ts +++ b/src/locales/fr/weather.ts @@ -5,40 +5,40 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; */ export const weather: SimpleTranslationEntries = { "sunnyStartMessage": "Les rayons du soleil brillent !", - "sunnyLapseMessage": "Les rayons du soleil brillent fort.", - "sunnyClearMessage": "Les rayons du soleil se dissipent.", + "sunnyLapseMessage": "Les rayons du soleil brillent fort !", + "sunnyClearMessage": "Les rayons du soleil s’affaiblissent !", "rainStartMessage": "Il commence à pleuvoir !", - "rainLapseMessage": "La pluie continue.", - "rainClearMessage": "La pluie s'est arrêtée.", + "rainLapseMessage": "La pluie continue de tomber !", + "rainClearMessage": "La pluie s’est arrêtée !", "sandstormStartMessage": "Une tempête de sable se prépare !", - "sandstormLapseMessage": "La tempête de sable fait rage.", - "sandstormClearMessage": "La tempête de sable se calme.", - "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} subit les dégâts\nde la tempête de sable !", + "sandstormLapseMessage": "La tempête de sable fait rage !", + "sandstormClearMessage": "La tempête de sable se calme !", + "sandstormDamageMessage": "La tempête de sable inflige des dégâts\nà {{pokemonPrefix}}{{pokemonName}} !", "hailStartMessage": "Il commence à grêler !", - "hailLapseMessage": "La grêle continue.", - "hailClearMessage": "La grêle s'est arrêtée.", - "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} subit les dégâts\nde la grêle !", + "hailLapseMessage": "La grêle continue de tomber !", + "hailClearMessage": "La grêle s’est arrêtée !", + "hailDamageMessage": "La grêle inflige des dégâts\nà {{pokemonPrefix}}{{pokemonName}} !", "snowStartMessage": "Il commence à neiger !", - "snowLapseMessage": "La neige continue de tomber.", - "snowClearMessage": "La neige s'est arrêtée.", + "snowLapseMessage": "Il y a une tempête de neige !", + "snowClearMessage": "La neige s’est arrêtée !", - "fogStartMessage": "Un brouillard épais émerge !", - "fogLapseMessage": "Le brouillard continue.", - "fogClearMessage": "Le brouillard a disparu.", + "fogStartMessage": "Le brouillard devient épais…", + "fogLapseMessage": "Le brouillard continue !", + "fogClearMessage": "Le brouillard s’est dissipé !", - "heavyRainStartMessage": "Une pluie battante s'abat soudainement !", + "heavyRainStartMessage": "Une pluie battante s’abat soudainement !", "heavyRainLapseMessage": "La pluie battante continue.", - "heavyRainClearMessage": "La pluie battante s'est arrêtée.", + "heavyRainClearMessage": "La pluie battante s’est arrêtée…", - "harshSunStartMessage": "Les rayons du soleil s'intensifient !", - "harshSunLapseMessage": "Le soleil est brûlant.", - "harshSunClearMessage": "Le soleil brûlant se dissipe.", + "harshSunStartMessage": "Les rayons du soleil s’intensifient !", + "harshSunLapseMessage": "Les rayons du soleil sont brulants !", + "harshSunClearMessage": "Les rayons du soleil s’affaiblissent !", - "strongWindsStartMessage": "Un vent violent se lève !", - "strongWindsLapseMessage": "Le vent souffle violemment.", - "strongWindsClearMessage": "Le vent violent s'est arrêté." -} \ No newline at end of file + "strongWindsStartMessage": "Un vent mystérieux se lève !", + "strongWindsLapseMessage": "Le vent mystérieux violemment !", + "strongWindsClearMessage": "Le vent mystérieux s’est dissipé…" +} From 04866e503a6b96ae5444b95346a0a32ec1b84843 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Ricardo=20Fleury=20Oliveira?= Date: Wed, 15 May 2024 16:24:47 -0300 Subject: [PATCH 21/46] Minor translating fixes and Save and Quit in ptBR (#928) * Minor fixes in menu-ui-handler * Minor fix in menu.ts --- src/locales/pt_BR/menu-ui-handler.ts | 16 ++++++++-------- src/locales/pt_BR/menu.ts | 2 +- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/src/locales/pt_BR/menu-ui-handler.ts b/src/locales/pt_BR/menu-ui-handler.ts index bfe863e38ce..5a60b614338 100644 --- a/src/locales/pt_BR/menu-ui-handler.ts +++ b/src/locales/pt_BR/menu-ui-handler.ts @@ -1,23 +1,23 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const menuUiHandler: SimpleTranslationEntries = { - "GAME_SETTINGS": 'Configurações', + "GAME_SETTINGS": "Configurações", "ACHIEVEMENTS": "Conquistas", "STATS": "Estatísticas", "VOUCHERS": "Vouchers", "EGG_LIST": "Incubadora", - "EGG_GACHA": "Gacha de Ovos", - "MANAGE_DATA": "Gerenciar Dados", + "EGG_GACHA": "Gacha de ovos", + "MANAGE_DATA": "Gerenciar dados", "COMMUNITY": "Comunidade", - "SAVE_AND_QUIT": "Save and Quit", + "SAVE_AND_QUIT": "Salvar e sair", "LOG_OUT": "Logout", "slot": "Slot {{slotNumber}}", - "importSession": "Importar Sessão", + "importSession": "Importar sessão", "importSlotSelect": "Selecione um slot para importar.", - "exportSession": "Exportar Sessão", + "exportSession": "Exportar sessão", "exportSlotSelect": "Selecione um slot para exportar.", - "importData": "Importar Dados", - "exportData": "Exportar Dados", + "importData": "Importar dados", + "exportData": "Exportar dados", "cancel": "Cancelar", "losingProgressionWarning": "Você vai perder todo o progresso desde o início da batalha. Confirmar?" } as const; \ No newline at end of file diff --git a/src/locales/pt_BR/menu.ts b/src/locales/pt_BR/menu.ts index 9cbde542037..868e8faa851 100644 --- a/src/locales/pt_BR/menu.ts +++ b/src/locales/pt_BR/menu.ts @@ -8,7 +8,7 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const menu: SimpleTranslationEntries = { "cancel": "Cancelar", "continue": "Continuar", - "dailyRun": "Desafio diário (Beta)", + "dailyRun": "Desafio Diário (Beta)", "loadGame": "Carregar Jogo", "newGame": "Novo Jogo", "selectGameMode": "Escolha um modo de jogo.", From 1b751dddec9032fad5b260779eee8a6592722bef Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Ricardo=20Fleury=20Oliveira?= Date: Wed, 15 May 2024 16:08:19 -0300 Subject: [PATCH 22/46] Update translations in pt_BR/menu.ts and pt_BR/weather.ts --- src/locales/pt_BR/menu.ts | 10 +++---- src/locales/pt_BR/weather.ts | 58 ++++++++++++++++++------------------ 2 files changed, 34 insertions(+), 34 deletions(-) diff --git a/src/locales/pt_BR/menu.ts b/src/locales/pt_BR/menu.ts index 868e8faa851..10f3fa4dff8 100644 --- a/src/locales/pt_BR/menu.ts +++ b/src/locales/pt_BR/menu.ts @@ -35,11 +35,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Você é um menino ou uma menina?", "boy": "Menino", "girl": "Menina", - "evolving": "What?\n{{pokemonName}} is evolving!", - "stoppedEvolving": "{{pokemonName}} stopped evolving.", - "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", - "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", - "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", + "evolving": "Que?\n{{pokemonName}} tá evoluindo!", + "stoppedEvolving": "{{pokemonName}} parou de evoluir.", + "pauseEvolutionsQuestion": "Gostaria de pausar evoluções para {{pokemonName}}?\nEvoluções podem ser religadas na tela de equipe.", + "evolutionsPaused": "Evoluções foram paradas para {{pokemonName}}.", + "evolutionDone": "Parabéns!\nSeu {{pokemonName}} evolui para {{evolvedPokemonName}}!", "dailyRankings": "Classificação Diária", "weeklyRankings": "Classificação Semanal", "noRankings": "Sem Classificação", diff --git a/src/locales/pt_BR/weather.ts b/src/locales/pt_BR/weather.ts index 999613f1566..de37cab7812 100644 --- a/src/locales/pt_BR/weather.ts +++ b/src/locales/pt_BR/weather.ts @@ -4,41 +4,41 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; * The weather namespace holds text displayed when weather is active during a battle */ export const weather: SimpleTranslationEntries = { - "sunnyStartMessage": "The sunlight got bright!", - "sunnyLapseMessage": "The sunlight is strong.", - "sunnyClearMessage": "The sunlight faded.", + "sunnyStartMessage": "A luz do sol ficou clara!", + "sunnyLapseMessage": "A luz do sol está forte.", + "sunnyClearMessage": "A luz do sol sumiu.", - "rainStartMessage": "A downpour started!", - "rainLapseMessage": "The downpour continues.", - "rainClearMessage": "The rain stopped.", + "rainStartMessage": "Começou a chover!", + "rainLapseMessage": "A chuva continua forte.", + "rainClearMessage": "A chuva parou.", - "sandstormStartMessage": "A sandstorm brewed!", - "sandstormLapseMessage": "The sandstorm rages.", - "sandstormClearMessage": "The sandstorm subsided.", - "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + "sandstormStartMessage": "Uma tempestade de areia se formou!", + "sandstormLapseMessage": "A tempestade de areia é violenta.", + "sandstormClearMessage": "A tempestade de areia diminuiu.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} é atingido\npela tempestade de areia!", - "hailStartMessage": "It started to hail!", - "hailLapseMessage": "Hail continues to fall.", - "hailClearMessage": "The hail stopped.", - "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + "hailStartMessage": "Começou a chover granizo!", + "hailLapseMessage": "Granizo cai do céu.", + "hailClearMessage": "O granizo parou.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} é atingido\npelo granizo!", - "snowStartMessage": "It started to snow!", - "snowLapseMessage": "The snow is falling down.", - "snowClearMessage": "The snow stopped.", + "snowStartMessage": "Começou a nevar!", + "snowLapseMessage": "A neve continua caindo.", + "snowClearMessage": "Parou de nevar.", - "fogStartMessage": "A thick fog emerged!", - "fogLapseMessage": "The fog continues.", - "fogClearMessage": "The fog disappeared.", + "fogStartMessage": "Uma névoa densa se formou!", + "fogLapseMessage": "A névoa continua forte.", + "fogClearMessage": "A névoa sumiu.", - "heavyRainStartMessage": "A heavy downpour started!", - "heavyRainLapseMessage": "The heavy downpour continues.", - "heavyRainClearMessage": "The heavy rain stopped.", + "heavyRainStartMessage": "Um temporal começou!", + "heavyRainLapseMessage": "O temporal continua forte.", + "heavyRainClearMessage": "O temporal parou.", - "harshSunStartMessage": "The sunlight got hot!", - "harshSunLapseMessage": "The sun is scorching hot.", - "harshSunClearMessage": "The harsh sunlight faded.", + "harshSunStartMessage": "A luz do sol está escaldante!", + "harshSunLapseMessage": "A luz do sol é intensa.", + "harshSunClearMessage": "A luz do sol enfraqueceu.", - "strongWindsStartMessage": "A heavy wind began!", - "strongWindsLapseMessage": "The wind blows intensely.", - "strongWindsClearMessage": "The heavy wind stopped." + "strongWindsStartMessage": "Ventos fortes apareceram!", + "strongWindsLapseMessage": "Os ventos fortes continuam.", + "strongWindsClearMessage": "Os ventos fortes diminuíram.", } \ No newline at end of file From a5bafe5c473695bf5ad4a9a25b36ea4a6d195ab2 Mon Sep 17 00:00:00 2001 From: Lugiad Date: Wed, 15 May 2024 23:43:28 +0200 Subject: [PATCH 23/46] Corrections to French menu.ts (#932) * Corrections to French menu.ts * Corrections to French menu.ts --- src/locales/fr/menu.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/locales/fr/menu.ts b/src/locales/fr/menu.ts index 7cf277889df..f6d5cfac063 100644 --- a/src/locales/fr/menu.ts +++ b/src/locales/fr/menu.ts @@ -30,11 +30,11 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "Es-tu un garçon ou une fille ?", "boy": "Garçon", "girl": "Fille", - "evolving": "Hein ?\n{{pokemonName}} évolue !", - "stoppedEvolving": "{{pokemonName}} a stoppé son évolution.", - "pauseEvolutionsQuestion": "Voulez-vous pauser les évolutions pour {{pokemonName}} ?\nLes évolutions peuvent être réactivées depuis l'écran d'équipe.", + "evolving": "Quoi ?\n{{pokemonName}} évolue !", + "stoppedEvolving": "Hein ?\n{{pokemonName}} n’évolue plus !", + "pauseEvolutionsQuestion": "Mettre en pause les évolutions pour {{pokemonName}} ?\nElles peuvent être réactivées depuis l’écran d’équipe.", "evolutionsPaused": "Les évolutions ont été mises en pause pour {{pokemonName}}.", - "evolutionDone": "Félicitations !\nVotre {{pokemonName}} a évolué en {{evolvedPokemonName}} !", + "evolutionDone": "Félicitations !\n{{pokemonName}} a évolué en {{evolvedPokemonName}} !", "dailyRankings": "Classement du Jour", "weeklyRankings": "Classement de la Semaine", "noRankings": "Pas de Classement", From 3781f581cc1044bec7470cc1c27b43ba271b895b Mon Sep 17 00:00:00 2001 From: Ice Date: Wed, 15 May 2024 18:32:40 -0500 Subject: [PATCH 24/46] Fix potion weight logic --- src/modifier/modifier-type.ts | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index 541e1833611..da8a19c019a 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -978,11 +978,11 @@ const modifierPool: ModifierPool = { new WeightedModifierType(modifierTypes.POKEBALL, 6), new WeightedModifierType(modifierTypes.RARE_CANDY, 2), new WeightedModifierType(modifierTypes.POTION, (party: Pokemon[]) => { - const thresholdPartyMemberCount = Math.min(party.filter(p => p.getInverseHp() >= 10 || p.getHpRatio() <= 0.875).length, 3); + const thresholdPartyMemberCount = Math.min(party.filter(p => (p.getInverseHp() >= 10 || p.getHpRatio() <= 0.875) && !p.isFainted()).length, 3); return thresholdPartyMemberCount * 3; }, 9), new WeightedModifierType(modifierTypes.SUPER_POTION, (party: Pokemon[]) => { - const thresholdPartyMemberCount = Math.min(party.filter(p => p.getInverseHp() >= 25 || p.getHpRatio() <= 0.75).length, 3); + const thresholdPartyMemberCount = Math.min(party.filter(p => (p.getInverseHp() >= 25 || p.getHpRatio() <= 0.75) && !p.isFainted()).length, 3); return thresholdPartyMemberCount; }, 3), new WeightedModifierType(modifierTypes.ETHER, (party: Pokemon[]) => { @@ -1016,16 +1016,16 @@ const modifierPool: ModifierPool = { return party.filter(p => p.isFainted()).length >= Math.ceil(party.length / 2) ? 1 : 0; }, 1), new WeightedModifierType(modifierTypes.HYPER_POTION, (party: Pokemon[]) => { - const thresholdPartyMemberCount = Math.min(party.filter(p => p.getInverseHp() >= 100 || p.getHpRatio() <= 0.625).length, 3); + const thresholdPartyMemberCount = Math.min(party.filter(p => (p.getInverseHp() >= 100 || p.getHpRatio() <= 0.625) && !p.isFainted()).length, 3); return thresholdPartyMemberCount * 3; }, 9), new WeightedModifierType(modifierTypes.MAX_POTION, (party: Pokemon[]) => { - const thresholdPartyMemberCount = Math.min(party.filter(p => p.getInverseHp() >= 150 || p.getHpRatio() <= 0.5).length, 3); + const thresholdPartyMemberCount = Math.min(party.filter(p => (p.getInverseHp() >= 150 || p.getHpRatio() <= 0.5) && !p.isFainted()).length, 3); return thresholdPartyMemberCount; }, 3), new WeightedModifierType(modifierTypes.FULL_RESTORE, (party: Pokemon[]) => { const statusEffectPartyMemberCount = Math.min(party.filter(p => p.hp && !!p.status).length, 3); - const thresholdPartyMemberCount = Math.floor((Math.min(party.filter(p => p.getInverseHp() >= 150 || p.getHpRatio() <= 0.5).length, 3) + statusEffectPartyMemberCount) / 2); + const thresholdPartyMemberCount = Math.floor((Math.min(party.filter(p => (p.getInverseHp() >= 150 || p.getHpRatio() <= 0.5) && !p.isFainted()).length, 3) + statusEffectPartyMemberCount) / 2); return thresholdPartyMemberCount; }, 3), new WeightedModifierType(modifierTypes.ELIXIR, (party: Pokemon[]) => { From b5ae8330a2bd667237cb924a0f7355dd3e5fe797 Mon Sep 17 00:00:00 2001 From: FanHua Date: Thu, 16 May 2024 12:32:45 +0800 Subject: [PATCH 25/46] Implements localization for ModifierType (#887) * Implements localization on ModifierType * All languages' translation fallback to EN locale * Fixed some typos * Add missing QUICK_CLAW translation entry --- src/locales/de/config.ts | 4 +- src/locales/de/modifier-type.ts | 409 +++++++++++++++++++ src/locales/en/config.ts | 4 +- src/locales/en/modifier-type.ts | 409 +++++++++++++++++++ src/locales/es/config.ts | 4 +- src/locales/es/modifier-type.ts | 409 +++++++++++++++++++ src/locales/fr/config.ts | 4 +- src/locales/fr/modifier-type.ts | 409 +++++++++++++++++++ src/locales/it/config.ts | 4 +- src/locales/it/modifier-type.ts | 409 +++++++++++++++++++ src/locales/pt_BR/config.ts | 4 +- src/locales/pt_BR/modifier-type.ts | 409 +++++++++++++++++++ src/locales/zh_CN/config.ts | 7 +- src/locales/zh_CN/growth.ts | 10 + src/locales/zh_CN/modifier-type.ts | 409 +++++++++++++++++++ src/modifier/modifier-type.ts | 618 +++++++++++++++++++---------- src/plugins/i18n.ts | 17 + 17 files changed, 3326 insertions(+), 213 deletions(-) create mode 100644 src/locales/de/modifier-type.ts create mode 100644 src/locales/en/modifier-type.ts create mode 100644 src/locales/es/modifier-type.ts create mode 100644 src/locales/fr/modifier-type.ts create mode 100644 src/locales/it/modifier-type.ts create mode 100644 src/locales/pt_BR/modifier-type.ts create mode 100644 src/locales/zh_CN/growth.ts create mode 100644 src/locales/zh_CN/modifier-type.ts diff --git a/src/locales/de/config.ts b/src/locales/de/config.ts index a9f4cd68297..04ad328b6ec 100644 --- a/src/locales/de/config.ts +++ b/src/locales/de/config.ts @@ -6,6 +6,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -30,5 +31,6 @@ export const deConfig = { starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, nature: nature, - growth: growth + growth: growth, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/de/modifier-type.ts b/src/locales/de/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/de/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/en/config.ts b/src/locales/en/config.ts index 9259aa5cbe1..0b3fd1505cc 100644 --- a/src/locales/en/config.ts +++ b/src/locales/en/config.ts @@ -6,6 +6,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -32,5 +33,6 @@ export const enConfig = { tutorial: tutorial, nature: nature, growth: growth, - weather: weather + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/en/modifier-type.ts b/src/locales/en/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/en/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/es/config.ts b/src/locales/es/config.ts index f6d6f2715d9..b38ae994c38 100644 --- a/src/locales/es/config.ts +++ b/src/locales/es/config.ts @@ -6,6 +6,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -32,5 +33,6 @@ export const esConfig = { tutorial: tutorial, nature: nature, growth: growth, - weather: weather + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/es/modifier-type.ts b/src/locales/es/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/es/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/fr/config.ts b/src/locales/fr/config.ts index 4179c758ff9..5ff44b46d31 100644 --- a/src/locales/fr/config.ts +++ b/src/locales/fr/config.ts @@ -6,6 +6,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -32,5 +33,6 @@ export const frConfig = { tutorial: tutorial, nature: nature, growth: growth, - weather: weather + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/fr/modifier-type.ts b/src/locales/fr/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/fr/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/it/config.ts b/src/locales/it/config.ts index 85e2e629184..d81143bf577 100644 --- a/src/locales/it/config.ts +++ b/src/locales/it/config.ts @@ -6,6 +6,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -32,5 +33,6 @@ export const itConfig = { tutorial: tutorial, nature: nature, growth: growth, - weather: weather + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/it/modifier-type.ts b/src/locales/it/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/it/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/pt_BR/config.ts b/src/locales/pt_BR/config.ts index 83d0641c8fa..af714a36316 100644 --- a/src/locales/pt_BR/config.ts +++ b/src/locales/pt_BR/config.ts @@ -5,6 +5,7 @@ import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; import { menuUiHandler } from "./menu-ui-handler"; +import { modifierType } from "./modifier-type"; import { move } from "./move"; import { nature } from "./nature"; import { pokeball } from "./pokeball"; @@ -30,5 +31,6 @@ export const ptBrConfig = { tutorial: tutorial, nature: nature, growth: growth, - weather: weather + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/pt_BR/modifier-type.ts b/src/locales/pt_BR/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/pt_BR/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/locales/zh_CN/config.ts b/src/locales/zh_CN/config.ts index 9a70eafb8e1..11339dca4c8 100644 --- a/src/locales/zh_CN/config.ts +++ b/src/locales/zh_CN/config.ts @@ -13,6 +13,8 @@ import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; import { nature } from "./nature"; import { weather } from "./weather"; +import { modifierType } from "./modifier-type"; +import { growth } from "./growth"; export const zhCnConfig = { @@ -29,7 +31,8 @@ export const zhCnConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, - nature: nature, - weather: weather + growth: growth, + weather: weather, + modifierType: modifierType, } \ No newline at end of file diff --git a/src/locales/zh_CN/growth.ts b/src/locales/zh_CN/growth.ts new file mode 100644 index 00000000000..a0d1cb5eeaa --- /dev/null +++ b/src/locales/zh_CN/growth.ts @@ -0,0 +1,10 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const growth: SimpleTranslationEntries = { + "Erratic": "Erratic", + "Fast": "Fast", + "Medium_Fast": "Medium Fast", + "Medium_Slow": "Medium Slow", + "Slow": "Slow", + "Fluctuating": "Fluctuating" +} as const; \ No newline at end of file diff --git a/src/locales/zh_CN/modifier-type.ts b/src/locales/zh_CN/modifier-type.ts new file mode 100644 index 00000000000..729644dc3b8 --- /dev/null +++ b/src/locales/zh_CN/modifier-type.ts @@ -0,0 +1,409 @@ +import { ModifierTypeTranslationEntries } from "#app/plugins/i18n"; + +export const modifierType: ModifierTypeTranslationEntries = { + ModifierType: { + "AddPokeballModifierType": { + name: "{{modifierCount}}x {{pokeballName}}", + description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + }, + "AddVoucherModifierType": { + name: "{{modifierCount}}x {{voucherTypeName}}", + description: "Receive {{voucherTypeName}} x{{modifierCount}}", + }, + "PokemonHeldItemModifierType": { + extra: { + "inoperable": "{{pokemonName}} can't take\nthis item!", + "tooMany": "{{pokemonName}} has too many\nof this item!", + } + }, + "PokemonHpRestoreModifierType": { + description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + extra: { + "fully": "Fully restores HP for one Pokémon", + "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + } + }, + "PokemonReviveModifierType": { + description: "Revives one Pokémon and restores {{restorePercent}}% HP", + }, + "PokemonStatusHealModifierType": { + description: "Heals any status ailment for one Pokémon", + }, + "PokemonPpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for one Pokémon move", + extra: { + "fully": "Restores all PP for one Pokémon move", + } + }, + "PokemonAllMovePpRestoreModifierType": { + description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + extra: { + "fully": "Restores all PP for all of one Pokémon's moves", + } + }, + "PokemonPpUpModifierType": { + description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + }, + "PokemonNatureChangeModifierType": { + name: "{{natureName}} Mint", + description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + }, + "DoubleBattleChanceBoosterModifierType": { + description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + }, + "TempBattleStatBoosterModifierType": { + description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + }, + "AttackTypeBoosterModifierType": { + description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + }, + "PokemonLevelIncrementModifierType": { + description: "Increases a Pokémon's level by 1", + }, + "AllPokemonLevelIncrementModifierType": { + description: "Increases all party members' level by 1", + }, + "PokemonBaseStatBoosterModifierType": { + description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + }, + "AllPokemonFullHpRestoreModifierType": { + description: "Restores 100% HP for all Pokémon", + }, + "AllPokemonFullReviveModifierType": { + description: "Revives all fainted Pokémon, fully restoring HP", + }, + "MoneyRewardModifierType": { + description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + extra: { + "small": "small", + "moderate": "moderate", + "large": "large", + }, + }, + "ExpBoosterModifierType": { + description: "Increases gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonExpBoosterModifierType": { + description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + }, + "PokemonFriendshipBoosterModifierType": { + description: "Increases friendship gain per victory by 50%", + }, + "PokemonMoveAccuracyBoosterModifierType": { + description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + }, + "PokemonMultiHitModifierType": { + description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + }, + "TmModifierType": { + name: "TM{{moveId}} - {{moveName}}", + description: "Teach {{moveName}} to a Pokémon", + }, + "EvolutionItemModifierType": { + description: "Causes certain Pokémon to evolve", + }, + "FormChangeItemModifierType": { + description: "Causes certain Pokémon to change form", + }, + "FusePokemonModifierType": { + description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + }, + "TerastallizeModifierType": { + name: "{{teraType}} Tera Shard", + description: "{{teraType}} Terastallizes the holder for up to 10 battles", + }, + "ContactHeldItemTransferChanceModifierType": { + description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + }, + "TurnHeldItemTransferModifierType": { + description: "Every turn, the holder acquires one held item from the foe", + }, + "EnemyAttackStatusEffectChanceModifierType": { + description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + }, + "EnemyEndureChanceModifierType": { + description: "Adds a {{chancePercent}}% chance of enduring a hit", + }, + + "RARE_CANDY": { name: "Rare Candy" }, + "RARER_CANDY": { name: "Rarer Candy" }, + + "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, + "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, + "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + + "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + + "POTION": { name: "Potion" }, + "SUPER_POTION": { name: "Super Potion" }, + "HYPER_POTION": { name: "Hyper Potion" }, + "MAX_POTION": { name: "Max Potion" }, + "FULL_RESTORE": { name: "Full Restore" }, + + "REVIVE": { name: "Revive" }, + "MAX_REVIVE": { name: "Max Revive" }, + + "FULL_HEAL": { name: "Full Heal" }, + + "SACRED_ASH": { name: "Sacred Ash" }, + + "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + + "ETHER": { name: "Ether" }, + "MAX_ETHER": { name: "Max Ether" }, + + "ELIXIR": { name: "Elixir" }, + "MAX_ELIXIR": { name: "Max Elixir" }, + + "PP_UP": { name: "PP Up" }, + "PP_MAX": { name: "PP Max" }, + + "LURE": { name: "Lure" }, + "SUPER_LURE": { name: "Super Lure" }, + "MAX_LURE": { name: "Max Lure" }, + + "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + + "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, + "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + + "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + + "EXP_CHARM": { name: "EXP. Charm" }, + "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, + "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + + "LUCKY_EGG": { name: "Lucky Egg" }, + "GOLDEN_EGG": { name: "Golden Egg" }, + + "SOOTHE_BELL": { name: "Soothe Bell" }, + + "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + + "NUGGET": { name: "Nugget" }, + "BIG_NUGGET": { name: "Big Nugget" }, + "RELIC_GOLD": { name: "Relic Gold" }, + + "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, + "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, + "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + + "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + + "GRIP_CLAW": { name: "Grip Claw" }, + "WIDE_LENS": { name: "Wide Lens" }, + + "MULTI_LENS": { name: "Multi Lens" }, + + "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, + "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + + "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + + "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + + "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + + "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + + "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, + "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + + "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + + "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + + "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + + "DNA_SPLICERS": { name: "DNA Splicers" }, + + "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + + "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, + "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, + "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, + "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + }, + TempBattleStatBoosterItem: { + "x_attack": "X Attack", + "x_defense": "X Defense", + "x_sp_atk": "X Sp. Atk", + "x_sp_def": "X Sp. Def", + "x_speed": "X Speed", + "x_accuracy": "X Accuracy", + "dire_hit": "Dire Hit", + }, + AttackTypeBoosterItem: { + "silk_scarf": "Silk Scarf", + "black_belt": "Black Belt", + "sharp_beak": "Sharp Beak", + "poison_barb": "Poison Barb", + "soft_sand": "Soft Sand", + "hard_stone": "Hard Stone", + "silver_powder": "Silver Powder", + "spell_tag": "Spell Tag", + "metal_coat": "Metal Coat", + "charcoal": "Charcoal", + "mystic_water": "Mystic Water", + "miracle_seed": "Miracle Seed", + "magnet": "Magnet", + "twisted_spoon": "Twisted Spoon", + "never-nelt_ice": "Never-Melt Ice", + "dragon_fang": "Dragon Fang", + "black_glasses": "Black Glasses", + "fairy_feather": "Fairy Feather", + }, + BaseStatBoosterItem: { + "hp_up": "HP Up", + "protein": "Protein", + "iron": "Iron", + "calcium": "Calcium", + "zinc": "Zinc", + "carbos": "Carbos", + }, + EvolutionItem: { + "NONE": "None", + + "LINKING_CORD": "Linking Cord", + "SUN_STONE": "Sun Stone", + "MOON_STONE": "Moon Stone", + "LEAF_STONE": "Leaf Stone", + "FIRE_STONE": "Fire Stone", + "WATER_STONE": "Water Stone", + "THUNDER_STONE": "Thunder Stone", + "ICE_STONE": "Ice Stone", + "DUSK_STONE": "Dusk Stone", + "DAWN_STONE": "Dawn Stone", + "SHINY_STONE": "Shiny Stone", + "CRACKED_POT": "Cracked Pot", + "SWEET_APPLE": "Sweet Apple", + "TART_APPLE": "Tart Apple", + "STRAWBERRY_SWEET": "Strawberry Sweet", + "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + + "CHIPPED_POT": "Chipped Pot", + "BLACK_AUGURITE": "Black Augurite", + "GALARICA_CUFF": "Galarica Cuff", + "GALARICA_WREATH": "Galarica Wreath", + "PEAT_BLOCK": "Peat Block", + "AUSPICIOUS_ARMOR": "Auspicious Armor", + "MALICIOUS_ARMOR": "Malicious Armor", + "MASTERPIECE_TEACUP": "Masterpiece Teacup", + "METAL_ALLOY": "Metal Alloy", + "SCROLL_OF_DARKNESS": "Scroll Of Darkness", + "SCROLL_OF_WATERS": "Scroll Of Waters", + "SYRUPY_APPLE": "Syrupy Apple", + }, + FormChangeItem: { + "NONE": "None", + + "ABOMASITE": "Abomasite", + "ABSOLITE": "Absolite", + "AERODACTYLITE": "Aerodactylite", + "AGGRONITE": "Aggronite", + "ALAKAZITE": "Alakazite", + "ALTARIANITE": "Altarianite", + "AMPHAROSITE": "Ampharosite", + "AUDINITE": "Audinite", + "BANETTITE": "Banettite", + "BEEDRILLITE": "Beedrillite", + "BLASTOISINITE": "Blastoisinite", + "BLAZIKENITE": "Blazikenite", + "CAMERUPTITE": "Cameruptite", + "CHARIZARDITE_X": "Charizardite X", + "CHARIZARDITE_Y": "Charizardite Y", + "DIANCITE": "Diancite", + "GALLADITE": "Galladite", + "GARCHOMPITE": "Garchompite", + "GARDEVOIRITE": "Gardevoirite", + "GENGARITE": "Gengarite", + "GLALITITE": "Glalitite", + "GYARADOSITE": "Gyaradosite", + "HERACRONITE": "Heracronite", + "HOUNDOOMINITE": "Houndoominite", + "KANGASKHANITE": "Kangaskhanite", + "LATIASITE": "Latiasite", + "LATIOSITE": "Latiosite", + "LOPUNNITE": "Lopunnite", + "LUCARIONITE": "Lucarionite", + "MANECTITE": "Manectite", + "MAWILITE": "Mawilite", + "MEDICHAMITE": "Medichamite", + "METAGROSSITE": "Metagrossite", + "MEWTWONITE_X": "Mewtwonite X", + "MEWTWONITE_Y": "Mewtwonite Y", + "PIDGEOTITE": "Pidgeotite", + "PINSIRITE": "Pinsirite", + "RAYQUAZITE": "Rayquazite", + "SABLENITE": "Sablenite", + "SALAMENCITE": "Salamencite", + "SCEPTILITE": "Sceptilite", + "SCIZORITE": "Scizorite", + "SHARPEDONITE": "Sharpedonite", + "SLOWBRONITE": "Slowbronite", + "STEELIXITE": "Steelixite", + "SWAMPERTITE": "Swampertite", + "TYRANITARITE": "Tyranitarite", + "VENUSAURITE": "Venusaurite", + + "BLUE_ORB": "Blue Orb", + "RED_ORB": "Red Orb", + "SHARP_METEORITE": "Sharp Meteorite", + "HARD_METEORITE": "Hard Meteorite", + "SMOOTH_METEORITE": "Smooth Meteorite", + "ADAMANT_CRYSTAL": "Adamant Crystal", + "LUSTROUS_ORB": "Lustrous Orb", + "GRISEOUS_CORE": "Griseous Core", + "REVEAL_GLASS": "Reveal Glass", + "GRACIDEA": "Gracidea", + "MAX_MUSHROOMS": "Max Mushrooms", + "DARK_STONE": "Dark Stone", + "LIGHT_STONE": "Light Stone", + "PRISON_BOTTLE": "Prison Bottle", + "N_LUNARIZER": "N Lunarizer", + "N_SOLARIZER": "N Solarizer", + "RUSTED_SWORD": "Rusted Sword", + "RUSTED_SHIELD": "Rusted Shield", + "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", + "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", + "WELLSPRING_MASK": "Wellspring Mask", + "HEARTHFLAME_MASK": "Hearthflame Mask", + "CORNERSTONE_MASK": "Cornerstone Mask", + "SHOCK_DRIVE": "Shock Drive", + "BURN_DRIVE": "Burn Drive", + "CHILL_DRIVE": "Chill Drive", + "DOUSE_DRIVE": "Douse Drive", + }, + TeraType: { + "UNKNOWN": "Unknown", + "NORMAL": "Normal", + "FIGHTING": "Fighting", + "FLYING": "Flying", + "POISON": "Poison", + "GROUND": "Ground", + "ROCK": "Rock", + "BUG": "Bug", + "GHOST": "Ghost", + "STEEL": "Steel", + "FIRE": "Fire", + "WATER": "Water", + "GRASS": "Grass", + "ELECTRIC": "Electric", + "PSYCHIC": "Psychic", + "ICE": "Ice", + "DRAGON": "Dragon", + "DARK": "Dark", + "FAIRY": "Fairy", + "STELLAR": "Stellar", + }, +} as const; \ No newline at end of file diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index da8a19c019a..c0f33521b33 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -3,7 +3,7 @@ import { AttackMove, allMoves } from '../data/move'; import { Moves } from "../data/enums/moves"; import { PokeballType, getPokeballCatchMultiplier, getPokeballName } from '../data/pokeball'; import Pokemon, { EnemyPokemon, PlayerPokemon, PokemonMove } from '../field/pokemon'; -import { EvolutionItem, SpeciesFriendshipEvolutionCondition, pokemonEvolutions } from '../data/pokemon-evolutions'; +import { EvolutionItem, pokemonEvolutions } from '../data/pokemon-evolutions'; import { Stat, getStatName } from '../data/pokemon-stat'; import { tmPoolTiers, tmSpecies } from '../data/tms'; import { Type } from '../data/type'; @@ -19,7 +19,7 @@ import { VoucherType, getVoucherTypeIcon, getVoucherTypeName } from '../system/v import { FormChangeItem, SpeciesFormChangeItemTrigger, pokemonFormChanges } from '../data/pokemon-forms'; import { ModifierTier } from './modifier-tier'; import { Nature, getNatureName, getNatureStatMultiplier } from '#app/data/nature'; -import { Localizable } from '#app/plugins/i18n'; +import i18next from '#app/plugins/i18n'; import { getModifierTierTextTint } from '#app/ui/text'; const outputModifierData = false; @@ -40,25 +40,27 @@ type NewModifierFunc = (type: ModifierType, args: any[]) => Modifier; export class ModifierType { public id: string; public generatorId: string; - public name: string; - protected description: string; + public localeKey: string; public iconImage: string; public group: string; public soundName: string; public tier: ModifierTier; protected newModifierFunc: NewModifierFunc; - constructor(name: string, description: string, newModifierFunc: NewModifierFunc, iconImage?: string, group?: string, soundName?: string) { - this.name = name; - this.description = description; - this.iconImage = iconImage || name?.replace(/[ \-]/g, '_')?.replace(/['\.]/g, '')?.toLowerCase(); + constructor(localeKey: string, iconImage: string, newModifierFunc: NewModifierFunc, group?: string, soundName?: string) { + this.localeKey = localeKey; + this.iconImage = iconImage; this.group = group || ''; this.soundName = soundName || 'restore'; this.newModifierFunc = newModifierFunc; } + get name(): string { + return i18next.t(`${this.localeKey}.name` as any); + } + getDescription(scene: BattleScene): string { - return this.description; + return i18next.t(`${this.localeKey}.description` as any); } setTier(tier: ModifierTier): void { @@ -114,7 +116,7 @@ export class ModifierTypeGenerator extends ModifierType { private genTypeFunc: ModifierTypeGeneratorFunc; constructor(genTypeFunc: ModifierTypeGeneratorFunc) { - super(null, null, null, null); + super(null, null, null); this.genTypeFunc = genTypeFunc; } @@ -133,58 +135,80 @@ export interface GeneratedPersistentModifierType { getPregenArgs(): any[]; } -class AddPokeballModifierType extends ModifierType implements Localizable { +class AddPokeballModifierType extends ModifierType { private pokeballType: PokeballType; private count: integer; - constructor(pokeballType: PokeballType, count: integer, iconImage?: string) { - super('', '', (_type, _args) => new Modifiers.AddPokeballModifier(this, pokeballType, count), iconImage, 'pb', 'pb_bounce_1'); + constructor(iconImage: string, pokeballType: PokeballType, count: integer) { + super('', iconImage, (_type, _args) => new Modifiers.AddPokeballModifier(this, pokeballType, count), 'pb', 'pb_bounce_1'); this.pokeballType = pokeballType; this.count = count; } - localize(): void { - // TODO: Actually use i18n to localize this description. - this.name = `${this.count}x ${getPokeballName(this.pokeballType)}`; - this.description = `Receive ${getPokeballName(this.pokeballType)} x${this.count} (Inventory: {AMOUNT}) \nCatch Rate: ${getPokeballCatchMultiplier(this.pokeballType) > -1 ? `${getPokeballCatchMultiplier(this.pokeballType)}x` : 'Certain'}`; - } - - getDescription(scene: BattleScene): string { - this.localize(); - return this.description.replace('{AMOUNT}', scene.pokeballCounts[this.pokeballType].toString()); + get name(): string { + return i18next.t(`modifierType:ModifierType.AddPokeballModifierType.name`, { + 'modifierCount': this.count, + 'pokeballName': getPokeballName(this.pokeballType), + }); } + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.AddPokeballModifierType.description`, { + 'modifierCount': this.count, + 'pokeballName': getPokeballName(this.pokeballType), + 'catchRate': getPokeballCatchMultiplier(this.pokeballType) > -1 ? `${getPokeballCatchMultiplier(this.pokeballType)}x` : '100%', + 'pokeballAmount': `${scene.pokeballCounts[this.pokeballType]}`, + }); + } } class AddVoucherModifierType extends ModifierType { + private voucherType: VoucherType; + private count: integer; + constructor(voucherType: VoucherType, count: integer) { - super(`${count}x ${getVoucherTypeName(voucherType)}`, `Receive ${getVoucherTypeName(voucherType)} x${count}`, - (_type, _args) => new Modifiers.AddVoucherModifier(this, voucherType, count), getVoucherTypeIcon(voucherType), 'voucher'); + super('', getVoucherTypeIcon(voucherType), (_type, _args) => new Modifiers.AddVoucherModifier(this, voucherType, count), 'voucher'); + this.count = count; + this.voucherType = voucherType; + } + + get name(): string { + return i18next.t(`modifierType:ModifierType.AddVoucherModifierType.name`, { + 'modifierCount': this.count, + 'voucherTypeName': getVoucherTypeName(this.voucherType), + }); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.AddVoucherModifierType.description`, { + 'modifierCount': this.count, + 'voucherTypeName': getVoucherTypeName(this.voucherType), + }); } } export class PokemonModifierType extends ModifierType { public selectFilter: PokemonSelectFilter; - constructor(name: string, description: string, newModifierFunc: NewModifierFunc, selectFilter?: PokemonSelectFilter, iconImage?: string, group?: string, soundName?: string) { - super(name, description, newModifierFunc, iconImage, group, soundName); + constructor(localeKey: string, iconImage: string, newModifierFunc: NewModifierFunc, selectFilter?: PokemonSelectFilter, group?: string, soundName?: string) { + super(localeKey, iconImage, newModifierFunc, group, soundName); this.selectFilter = selectFilter; } } export class PokemonHeldItemModifierType extends PokemonModifierType { - constructor(name: string, description: string, newModifierFunc: NewModifierFunc, iconImage?: string, group?: string, soundName?: string) { - super(name, description, newModifierFunc, (pokemon: PlayerPokemon) => { + constructor(localeKey: string, iconImage: string, newModifierFunc: NewModifierFunc, group?: string, soundName?: string) { + super(localeKey, iconImage, newModifierFunc, (pokemon: PlayerPokemon) => { const dummyModifier = this.newModifier(pokemon); const matchingModifier = pokemon.scene.findModifier(m => m instanceof Modifiers.PokemonHeldItemModifier && m.pokemonId === pokemon.id && m.matchType(dummyModifier)) as Modifiers.PokemonHeldItemModifier; const maxStackCount = dummyModifier.getMaxStackCount(pokemon.scene); if (!maxStackCount) - return `${pokemon.name} can\'t take\nthis item!`; + return i18next.t(`modifierType:ModifierType.PokemonHeldItemModifierType.extra.inoperable`, { 'pokemonName': pokemon.name }); if (matchingModifier && matchingModifier.stackCount === maxStackCount) - return `${pokemon.name} has too many\nof this item!`; + return i18next.t(`modifierType:ModifierType.PokemonHeldItemModifierType.extra.tooMany`, { 'pokemonName': pokemon.name }); return null; - }, iconImage, group, soundName); + }, group, soundName); } newModifier(...args: any[]): Modifiers.PokemonHeldItemModifier { @@ -197,57 +221,72 @@ export class PokemonHpRestoreModifierType extends PokemonModifierType { protected restorePercent: integer; protected healStatus: boolean; - constructor(name: string, restorePoints: integer, restorePercent: integer, healStatus: boolean = false, newModifierFunc?: NewModifierFunc, selectFilter?: PokemonSelectFilter, iconImage?: string, group?: string) { - super(name, restorePoints ? `Restores ${restorePoints} HP or ${restorePercent}% HP for one Pokémon, whichever is higher` : `Fully restores HP for one Pokémon${healStatus ? ' and heals any status ailment' : ''}`, - newModifierFunc || ((_type, args) => new Modifiers.PokemonHpRestoreModifier(this, (args[0] as PlayerPokemon).id, this.restorePoints, this.restorePercent, this.healStatus, false)), + constructor(localeKey: string, iconImage: string, restorePoints: integer, restorePercent: integer, healStatus: boolean = false, newModifierFunc?: NewModifierFunc, selectFilter?: PokemonSelectFilter, group?: string) { + super(localeKey, iconImage, newModifierFunc || ((_type, args) => new Modifiers.PokemonHpRestoreModifier(this, (args[0] as PlayerPokemon).id, this.restorePoints, this.restorePercent, this.healStatus, false)), selectFilter || ((pokemon: PlayerPokemon) => { if (!pokemon.hp || (pokemon.hp >= pokemon.getMaxHp() && (!this.healStatus || !pokemon.status))) return PartyUiHandler.NoEffectMessage; return null; - }), iconImage, group || 'potion'); + }), group || 'potion'); this.restorePoints = restorePoints; this.restorePercent = restorePercent; this.healStatus = healStatus; } + + getDescription(scene: BattleScene): string { + return this.restorePoints + ? i18next.t(`modifierType:ModifierType.PokemonHpRestoreModifierType.description`, { + restorePoints: this.restorePoints, + restorePercent: this.restorePercent, + }) + : this.healStatus + ? i18next.t(`modifierType:ModifierType.PokemonHpRestoreModifierType.extra.fullyWithStatus`) + : i18next.t(`modifierType:ModifierType.PokemonHpRestoreModifierType.extra.fully`); + } } export class PokemonReviveModifierType extends PokemonHpRestoreModifierType { - constructor(name: string, restorePercent: integer, iconImage?: string) { - super(name, 0, restorePercent, false, (_type, args) => new Modifiers.PokemonHpRestoreModifier(this, (args[0] as PlayerPokemon).id, 0, this.restorePercent, false, true), + constructor(localeKey: string, iconImage: string, restorePercent: integer) { + super(localeKey, iconImage, 0, restorePercent, false, (_type, args) => new Modifiers.PokemonHpRestoreModifier(this, (args[0] as PlayerPokemon).id, 0, this.restorePercent, false, true), ((pokemon: PlayerPokemon) => { if (!pokemon.isFainted()) return PartyUiHandler.NoEffectMessage; return null; - }), iconImage, 'revive'); + }), 'revive'); - this.description = `Revives one Pokémon and restores ${restorePercent}% HP`; this.selectFilter = (pokemon: PlayerPokemon) => { if (pokemon.hp) return PartyUiHandler.NoEffectMessage; return null; }; } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonReviveModifierType.description`, { restorePercent: this.restorePercent }); + } } export class PokemonStatusHealModifierType extends PokemonModifierType { - constructor(name: string) { - super(name, `Heals any status ailment for one Pokémon`, - ((_type, args) => new Modifiers.PokemonStatusHealModifier(this, (args[0] as PlayerPokemon).id)), + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, ((_type, args) => new Modifiers.PokemonStatusHealModifier(this, (args[0] as PlayerPokemon).id)), ((pokemon: PlayerPokemon) => { if (!pokemon.hp || !pokemon.status) return PartyUiHandler.NoEffectMessage; return null; })); } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonStatusHealModifierType.description`); + } } export abstract class PokemonMoveModifierType extends PokemonModifierType { public moveSelectFilter: PokemonMoveSelectFilter; - constructor(name: string, description: string, newModifierFunc: NewModifierFunc, selectFilter?: PokemonSelectFilter, moveSelectFilter?: PokemonMoveSelectFilter, - iconImage?: string, group?: string) { - super(name, description, newModifierFunc, selectFilter, iconImage, group); + constructor(localeKey: string, iconImage: string, newModifierFunc: NewModifierFunc, selectFilter?: PokemonSelectFilter, moveSelectFilter?: PokemonMoveSelectFilter, group?: string) { + super(localeKey, iconImage, newModifierFunc, selectFilter, group); this.moveSelectFilter = moveSelectFilter; } @@ -256,101 +295,136 @@ export abstract class PokemonMoveModifierType extends PokemonModifierType { export class PokemonPpRestoreModifierType extends PokemonMoveModifierType { protected restorePoints: integer; - constructor(name: string, restorePoints: integer, iconImage?: string) { - super(name, `Restores ${restorePoints > -1 ? restorePoints : 'all'} PP for one Pokémon move`, (_type, args) => new Modifiers.PokemonPpRestoreModifier(this, (args[0] as PlayerPokemon).id, (args[1] as integer), this.restorePoints), + constructor(localeKey: string, iconImage: string, restorePoints: integer) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonPpRestoreModifier(this, (args[0] as PlayerPokemon).id, (args[1] as integer), this.restorePoints), (_pokemon: PlayerPokemon) => { return null; }, (pokemonMove: PokemonMove) => { if (!pokemonMove.ppUsed) return PartyUiHandler.NoEffectMessage; return null; - }, iconImage, 'ether'); + }, 'ether'); this.restorePoints = restorePoints; } + + getDescription(scene: BattleScene): string { + return this.restorePoints > -1 + ? i18next.t(`modifierType:ModifierType.PokemonPpRestoreModifierType.description`, { restorePoints: this.restorePoints }) + : i18next.t(`modifierType:ModifierType.PokemonPpRestoreModifierType.extra.fully`) + ; + } } export class PokemonAllMovePpRestoreModifierType extends PokemonModifierType { protected restorePoints: integer; - constructor(name: string, restorePoints: integer, iconImage?: string) { - super(name, `Restores ${restorePoints > -1 ? restorePoints : 'all'} PP for all of one Pokémon's moves`, (_type, args) => new Modifiers.PokemonAllMovePpRestoreModifier(this, (args[0] as PlayerPokemon).id, this.restorePoints), + constructor(localeKey: string, iconImage: string, restorePoints: integer) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonAllMovePpRestoreModifier(this, (args[0] as PlayerPokemon).id, this.restorePoints), (pokemon: PlayerPokemon) => { if (!pokemon.getMoveset().filter(m => m.ppUsed).length) return PartyUiHandler.NoEffectMessage; return null; - }, iconImage, 'elixir'); + }, 'elixir'); this.restorePoints = restorePoints; } + + getDescription(scene: BattleScene): string { + return this.restorePoints > -1 + ? i18next.t(`modifierType:ModifierType.PokemonAllMovePpRestoreModifierType.description`, { restorePoints: this.restorePoints }) + : i18next.t(`modifierType:ModifierType.PokemonAllMovePpRestoreModifierType.extra.fully`) + ; + } } export class PokemonPpUpModifierType extends PokemonMoveModifierType { protected upPoints: integer; - constructor(name: string, upPoints: integer, iconImage?: string) { - super(name, `Permanently increases PP for one Pokémon move by ${upPoints} for every 5 maximum PP (maximum 3)`, (_type, args) => new Modifiers.PokemonPpUpModifier(this, (args[0] as PlayerPokemon).id, (args[1] as integer), this.upPoints), + constructor(localeKey: string, iconImage: string, upPoints: integer) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonPpUpModifier(this, (args[0] as PlayerPokemon).id, (args[1] as integer), this.upPoints), (_pokemon: PlayerPokemon) => { return null; }, (pokemonMove: PokemonMove) => { if (pokemonMove.getMove().pp < 5 || pokemonMove.ppUp >= 3) return PartyUiHandler.NoEffectMessage; return null; - }, iconImage, 'ppUp'); + }, 'ppUp'); this.upPoints = upPoints; } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonPpUpModifierType.description`, { upPoints: this.upPoints }); + } } export class PokemonNatureChangeModifierType extends PokemonModifierType { protected nature: Nature; constructor(nature: Nature) { - super(`${getNatureName(nature)} Mint`, `Changes a Pokémon\'s nature to ${getNatureName(nature, true, true, true)} and permanently unlocks the nature for the starter.`, ((_type, args) => new Modifiers.PokemonNatureChangeModifier(this, (args[0] as PlayerPokemon).id, this.nature)), + super('', `mint_${Utils.getEnumKeys(Stat).find(s => getNatureStatMultiplier(nature, Stat[s]) > 1)?.toLowerCase() || 'neutral' }`, ((_type, args) => new Modifiers.PokemonNatureChangeModifier(this, (args[0] as PlayerPokemon).id, this.nature)), ((pokemon: PlayerPokemon) => { if (pokemon.getNature() === this.nature) return PartyUiHandler.NoEffectMessage; return null; - }), `mint_${Utils.getEnumKeys(Stat).find(s => getNatureStatMultiplier(nature, Stat[s]) > 1)?.toLowerCase() || 'neutral' }`, 'mint'); + }), 'mint'); this.nature = nature; } + + get name(): string { + return i18next.t(`modifierType:ModifierType.PokemonNatureChangeModifierType.name`, { natureName: getNatureName(this.nature) }); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonNatureChangeModifierType.description`, { natureName: getNatureName(this.nature, true, true, true) }); + } } export class RememberMoveModifierType extends PokemonModifierType { - constructor(name: string, description: string, iconImage?: string, group?: string) { - super(name, description, (type, args) => new Modifiers.RememberMoveModifier(type, (args[0] as PlayerPokemon).id, (args[1] as integer)), + constructor(localeKey: string, iconImage: string, group?: string) { + super(localeKey, iconImage, (type, args) => new Modifiers.RememberMoveModifier(type, (args[0] as PlayerPokemon).id, (args[1] as integer)), (pokemon: PlayerPokemon) => { if (!pokemon.getLearnableLevelMoves().length) return PartyUiHandler.NoEffectMessage; return null; - }, iconImage, group); + }, group); } } export class DoubleBattleChanceBoosterModifierType extends ModifierType { public battleCount: integer; - constructor(name: string, battleCount: integer) { - super(name, `Doubles the chance of an encounter being a double battle for ${battleCount} battles`, (_type, _args) => new Modifiers.DoubleBattleChanceBoosterModifier(this, this.battleCount), - null, 'lure'); + constructor(localeKey: string, iconImage: string, battleCount: integer) { + super(localeKey, iconImage, (_type, _args) => new Modifiers.DoubleBattleChanceBoosterModifier(this, this.battleCount), 'lure'); this.battleCount = battleCount; } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.DoubleBattleChanceBoosterModifierType.description`, { battleCount: this.battleCount }); + } } export class TempBattleStatBoosterModifierType extends ModifierType implements GeneratedPersistentModifierType { public tempBattleStat: TempBattleStat; constructor(tempBattleStat: TempBattleStat) { - super(getTempBattleStatBoosterItemName(tempBattleStat), - `Increases the ${getTempBattleStatName(tempBattleStat)} of all party members by 1 stage for 5 battles`, - (_type, _args) => new Modifiers.TempBattleStatBoosterModifier(this, this.tempBattleStat), - getTempBattleStatBoosterItemName(tempBattleStat).replace(/\./g, '').replace(/[ ]/g, '_').toLowerCase()); + super('', getTempBattleStatBoosterItemName(tempBattleStat).replace(/\./g, '').replace(/[ ]/g, '_').toLowerCase(), + (_type, _args) => new Modifiers.TempBattleStatBoosterModifier(this, this.tempBattleStat)); this.tempBattleStat = tempBattleStat; } + get name(): string { + return i18next.t(`modifierType:TempBattleStatBoosterItem.${getTempBattleStatBoosterItemName(this.tempBattleStat).replace(/\./g, '').replace(/[ ]/g, '_').toLowerCase()}`); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.TempBattleStatBoosterModifierType.description`, { tempBattleStatName: getTempBattleStatName(this.tempBattleStat) }); + } + getPregenArgs(): any[] { return [ this.tempBattleStat ]; } @@ -360,13 +434,19 @@ export class BerryModifierType extends PokemonHeldItemModifierType implements Ge private berryType: BerryType; constructor(berryType: BerryType) { - super(getBerryName(berryType), getBerryEffectDescription(berryType), - (type, args) => new Modifiers.BerryModifier(type, (args[0] as Pokemon).id, berryType), - null, 'berry'); + super('', `${BerryType[berryType].toLowerCase()}_berry`, (type, args) => new Modifiers.BerryModifier(type, (args[0] as Pokemon).id, berryType), 'berry'); this.berryType = berryType; } + get name(): string { + return getBerryName(this.berryType); + } + + getDescription(scene: BattleScene): string { + return getBerryEffectDescription(this.berryType); + } + getPregenArgs(): any[] { return [ this.berryType ]; } @@ -418,29 +498,44 @@ export class AttackTypeBoosterModifierType extends PokemonHeldItemModifierType i public boostPercent: integer; constructor(moveType: Type, boostPercent: integer) { - super(getAttackTypeBoosterItemName(moveType), `Increases the power of a Pokémon's ${Utils.toReadableString(Type[moveType])}-type moves by 20%`, - (_type, args) => new Modifiers.AttackTypeBoosterModifier(this, (args[0] as Pokemon).id, moveType, boostPercent), - `${getAttackTypeBoosterItemName(moveType).replace(/[ \-]/g, '_').toLowerCase()}`); + super('', `${getAttackTypeBoosterItemName(moveType).replace(/[ \-]/g, '_').toLowerCase()}`, + (_type, args) => new Modifiers.AttackTypeBoosterModifier(this, (args[0] as Pokemon).id, moveType, boostPercent)); this.moveType = moveType; this.boostPercent = boostPercent; } + get name(): string { + return i18next.t(`modifierType:AttackTypeBoosterItem.${getAttackTypeBoosterItemName(this.moveType).replace(/[ \-]/g, '_').toLowerCase()}`); + } + + getDescription(scene: BattleScene): string { + // TODO: Need getTypeName? + return i18next.t(`modifierType:ModifierType.AttackTypeBoosterModifierType.description`, { moveType: Utils.toReadableString(Type[this.moveType]) }); + } + getPregenArgs(): any[] { return [ this.moveType ]; } } export class PokemonLevelIncrementModifierType extends PokemonModifierType { - constructor(name: string, iconImage?: string) { - super(name, `Increases a Pokémon\'s level by 1`, (_type, args) => new Modifiers.PokemonLevelIncrementModifier(this, (args[0] as PlayerPokemon).id), - (_pokemon: PlayerPokemon) => null, iconImage); + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonLevelIncrementModifier(this, (args[0] as PlayerPokemon).id), (_pokemon: PlayerPokemon) => null); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonLevelIncrementModifierType.description`); } } export class AllPokemonLevelIncrementModifierType extends ModifierType { - constructor(name: string, iconImage?: string) { - super(name, `Increases all party members' level by 1`, (_type, _args) => new Modifiers.PokemonLevelIncrementModifier(this, -1), iconImage); + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, (_type, _args) => new Modifiers.PokemonLevelIncrementModifier(this, -1)); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.AllPokemonLevelIncrementModifierType.description`); } } @@ -462,73 +557,127 @@ function getBaseStatBoosterItemName(stat: Stat) { } export class PokemonBaseStatBoosterModifierType extends PokemonHeldItemModifierType implements GeneratedPersistentModifierType { + private localeName: string; private stat: Stat; - constructor(name: string, stat: Stat, _iconImage?: string) { - super(name, `Increases the holder's base ${getStatName(stat)} by 10%. The higher your IVs, the higher the stack limit.`, (_type, args) => new Modifiers.PokemonBaseStatModifier(this, (args[0] as Pokemon).id, this.stat)); + constructor(localeName: string, stat: Stat) { + super('', localeName.replace(/[ \-]/g, '_').toLowerCase(), (_type, args) => new Modifiers.PokemonBaseStatModifier(this, (args[0] as Pokemon).id, this.stat)); + this.localeName = localeName; this.stat = stat; } + get name(): string { + return i18next.t(`modifierType:BaseStatBoosterItem.${this.localeName.replace(/[ \-]/g, '_').toLowerCase()}`); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonBaseStatBoosterModifierType.description`, { statName: getStatName(this.stat) }); + } + getPregenArgs(): any[] { return [ this.stat ]; } } class AllPokemonFullHpRestoreModifierType extends ModifierType { - constructor(name: string, description?: string, newModifierFunc?: NewModifierFunc, iconImage?: string) { - super(name, description || `Restores 100% HP for all Pokémon`, newModifierFunc || ((_type, _args) => new Modifiers.PokemonHpRestoreModifier(this, -1, 0, 100, false)), iconImage); + private descriptionKey: string; + + constructor(localeKey: string, iconImage: string, descriptionKey?: string, newModifierFunc?: NewModifierFunc) { + super(localeKey, iconImage, newModifierFunc || ((_type, _args) => new Modifiers.PokemonHpRestoreModifier(this, -1, 0, 100, false))); + + this.descriptionKey = descriptionKey; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`${this.descriptionKey || `modifierType:ModifierType.AllPokemonFullHpRestoreModifierType`}.description` as any); } } class AllPokemonFullReviveModifierType extends AllPokemonFullHpRestoreModifierType { - constructor(name: string, iconImage?: string) { - super(name, `Revives all fainted Pokémon, fully restoring HP`, (_type, _args) => new Modifiers.PokemonHpRestoreModifier(this, -1, 0, 100, false, true), iconImage); + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, `modifierType:ModifierType.AllPokemonFullReviveModifierType`, (_type, _args) => new Modifiers.PokemonHpRestoreModifier(this, -1, 0, 100, false, true)); } } export class MoneyRewardModifierType extends ModifierType { private moneyMultiplier: number; + private moneyMultiplierDescriptorKey: string; - constructor(name: string, moneyMultiplier: number, moneyMultiplierDescriptor: string, iconImage?: string) { - super(name, `Grants a ${moneyMultiplierDescriptor} amount of money (₽{AMOUNT})`, (_type, _args) => new Modifiers.MoneyRewardModifier(this, moneyMultiplier), iconImage, 'money', 'buy'); + constructor(localeKey: string, iconImage: string, moneyMultiplier: number, moneyMultiplierDescriptorKey: string) { + super(localeKey, iconImage, (_type, _args) => new Modifiers.MoneyRewardModifier(this, moneyMultiplier), 'money', 'buy'); this.moneyMultiplier = moneyMultiplier; + this.moneyMultiplierDescriptorKey = moneyMultiplierDescriptorKey; } getDescription(scene: BattleScene): string { - return this.description.replace('{AMOUNT}', scene.getWaveMoneyAmount(this.moneyMultiplier).toLocaleString('en-US')); + return i18next.t(`modifierType:ModifierType.MoneyRewardModifierType.description`, { + moneyMultiplier: i18next.t(this.moneyMultiplierDescriptorKey as any), + moneyAmount: scene.getWaveMoneyAmount(this.moneyMultiplier).toLocaleString('en-US'), + }); } } export class ExpBoosterModifierType extends ModifierType { - constructor(name: string, boostPercent: integer, iconImage?: string) { - super(name, `Increases gain of EXP. Points by ${boostPercent}%`, () => new Modifiers.ExpBoosterModifier(this, boostPercent), iconImage); + private boostPercent: integer; + + constructor(localeKey: string, iconImage: string, boostPercent: integer) { + super(localeKey, iconImage, () => new Modifiers.ExpBoosterModifier(this, boostPercent)); + + this.boostPercent = boostPercent; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.ExpBoosterModifierType.description`, { boostPercent: this.boostPercent }); } } export class PokemonExpBoosterModifierType extends PokemonHeldItemModifierType { - constructor(name: string, boostPercent: integer, iconImage?: string) { - super(name, `Increases the holder's gain of EXP. Points by ${boostPercent}%`, (_type, args) => new Modifiers.PokemonExpBoosterModifier(this, (args[0] as Pokemon).id, boostPercent), - iconImage); + private boostPercent: integer; + + constructor(localeKey: string, iconImage: string, boostPercent: integer) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonExpBoosterModifier(this, (args[0] as Pokemon).id, boostPercent)); + + this.boostPercent = boostPercent; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonExpBoosterModifierType.description`, { boostPercent: this.boostPercent }); } } export class PokemonFriendshipBoosterModifierType extends PokemonHeldItemModifierType { - constructor(name: string, iconImage?: string) { - super(name,'Increases friendship gain per victory by 50%', (_type, args) => new Modifiers.PokemonFriendshipBoosterModifier(this, (args[0] as Pokemon).id), iconImage); + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonFriendshipBoosterModifier(this, (args[0] as Pokemon).id)); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonFriendshipBoosterModifierType.description`); } } export class PokemonMoveAccuracyBoosterModifierType extends PokemonHeldItemModifierType { - constructor(name: string, amount: integer, iconImage?: string, group?: string, soundName?: string) { - super(name, `Increases move accuracy by ${amount} (maximum 100)`, (_type, args) => new Modifiers.PokemonMoveAccuracyBoosterModifier(this, (args[0] as Pokemon).id, amount), iconImage, group, soundName); + private amount: integer; + + constructor(localeKey: string, iconImage: string, amount: integer, group?: string, soundName?: string) { + super(localeKey, iconImage, (_type, args) => new Modifiers.PokemonMoveAccuracyBoosterModifier(this, (args[0] as Pokemon).id, amount), group, soundName); + + this.amount = amount; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonMoveAccuracyBoosterModifierType.description`, { accuracyAmount: this.amount }); } } export class PokemonMultiHitModifierType extends PokemonHeldItemModifierType { - constructor(name: string, iconImage?: string) { - super(name, `Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively.`, (type, args) => new Modifiers.PokemonMultiHitModifier(type as PokemonMultiHitModifierType, (args[0] as Pokemon).id), iconImage); + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, (type, args) => new Modifiers.PokemonMultiHitModifier(type as PokemonMultiHitModifierType, (args[0] as Pokemon).id)); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.PokemonMultiHitModifierType.description`); } } @@ -536,22 +685,33 @@ export class TmModifierType extends PokemonModifierType { public moveId: Moves; constructor(moveId: Moves) { - super(`TM${Utils.padInt(Object.keys(tmSpecies).indexOf(moveId.toString()) + 1, 3)} - ${allMoves[moveId].name}`, `Teach ${allMoves[moveId].name} to a Pokémon`, (_type, args) => new Modifiers.TmModifier(this, (args[0] as PlayerPokemon).id), + super('', `tm_${Type[allMoves[moveId].type].toLowerCase()}`, (_type, args) => new Modifiers.TmModifier(this, (args[0] as PlayerPokemon).id), (pokemon: PlayerPokemon) => { if (pokemon.compatibleTms.indexOf(moveId) === -1 || pokemon.getMoveset().filter(m => m?.moveId === moveId).length) return PartyUiHandler.NoEffectMessage; return null; - }, `tm_${Type[allMoves[moveId].type].toLowerCase()}`, 'tm'); + }, 'tm'); this.moveId = moveId; } + + get name(): string { + return i18next.t(`modifierType:ModifierType.TmModifierType.name`, { + moveId: Utils.padInt(Object.keys(tmSpecies).indexOf(this.moveId.toString()) + 1, 3), + moveName: allMoves[this.moveId].name, + }); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.TmModifierType.description`, { moveName: allMoves[this.moveId].name }); + } } export class EvolutionItemModifierType extends PokemonModifierType implements GeneratedPersistentModifierType { public evolutionItem: EvolutionItem; constructor(evolutionItem: EvolutionItem) { - super(Utils.toReadableString(EvolutionItem[evolutionItem]), `Causes certain Pokémon to evolve`, (_type, args) => new Modifiers.EvolutionItemModifier(this, (args[0] as PlayerPokemon).id), + super('', EvolutionItem[evolutionItem].toLowerCase(), (_type, args) => new Modifiers.EvolutionItemModifier(this, (args[0] as PlayerPokemon).id), (pokemon: PlayerPokemon) => { if (pokemonEvolutions.hasOwnProperty(pokemon.species.speciesId) && pokemonEvolutions[pokemon.species.speciesId].filter(e => e.item === this.evolutionItem && (!e.condition || e.condition.predicate(pokemon))).length && (pokemon.getFormKey() !== SpeciesFormKey.GIGANTAMAX)) @@ -561,10 +721,18 @@ export class EvolutionItemModifierType extends PokemonModifierType implements Ge return null; return PartyUiHandler.NoEffectMessage; - }, EvolutionItem[evolutionItem].toLowerCase()); + }); this.evolutionItem = evolutionItem; } + + get name(): string { + return i18next.t(`modifierType:EvolutionItem.${EvolutionItem[this.evolutionItem]}`); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.EvolutionItemModifierType.description`); + } getPregenArgs(): any[] { return [ this.evolutionItem ]; @@ -575,31 +743,43 @@ export class FormChangeItemModifierType extends PokemonModifierType implements G public formChangeItem: FormChangeItem; constructor(formChangeItem: FormChangeItem) { - super(Utils.toReadableString(FormChangeItem[formChangeItem]), `Causes certain Pokémon to change form`, (_type, args) => new Modifiers.PokemonFormChangeItemModifier(this, (args[0] as PlayerPokemon).id, formChangeItem, true), + super('', FormChangeItem[formChangeItem].toLowerCase(), (_type, args) => new Modifiers.PokemonFormChangeItemModifier(this, (args[0] as PlayerPokemon).id, formChangeItem, true), (pokemon: PlayerPokemon) => { if (pokemonFormChanges.hasOwnProperty(pokemon.species.speciesId) && !!pokemonFormChanges[pokemon.species.speciesId].find(fc => fc.trigger.hasTriggerType(SpeciesFormChangeItemTrigger) && (fc.trigger as SpeciesFormChangeItemTrigger).item === this.formChangeItem)) return null; return PartyUiHandler.NoEffectMessage; - }, FormChangeItem[formChangeItem].toLowerCase()); + }); this.formChangeItem = formChangeItem; } + get name(): string { + return i18next.t(`modifierType:FormChangeItem.${FormChangeItem[this.formChangeItem]}`); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.FormChangeItemModifierType.description`); + } + getPregenArgs(): any[] { return [ this.formChangeItem ]; } } export class FusePokemonModifierType extends PokemonModifierType { - constructor(name: string, iconImage?: string) { - super(name, 'Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)', (_type, args) => new Modifiers.FusePokemonModifier(this, (args[0] as PlayerPokemon).id, (args[1] as PlayerPokemon).id), + constructor(localeKey: string, iconImage: string) { + super(localeKey, iconImage, (_type, args) => new Modifiers.FusePokemonModifier(this, (args[0] as PlayerPokemon).id, (args[1] as PlayerPokemon).id), (pokemon: PlayerPokemon) => { if (pokemon.isFusion()) return PartyUiHandler.NoEffectMessage; return null; - }, iconImage); + }); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.FusePokemonModifierType.description`); } } @@ -712,37 +892,78 @@ export class TerastallizeModifierType extends PokemonHeldItemModifierType implem private teraType: Type; constructor(teraType: Type) { - super(`${Utils.toReadableString(Type[teraType])} Tera Shard`, `${Utils.toReadableString(Type[teraType])} Terastallizes the holder for up to 10 battles`, (type, args) => new Modifiers.TerastallizeModifier(type as TerastallizeModifierType, (args[0] as Pokemon).id, teraType), null, 'tera_shard'); + super('', `${Type[teraType].toLowerCase()}_tera_shard`, (type, args) => new Modifiers.TerastallizeModifier(type as TerastallizeModifierType, (args[0] as Pokemon).id, teraType), 'tera_shard'); this.teraType = teraType; } + get name(): string { + return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.name`, { teraType: i18next.t(`modifierType:FormChangeItem.${Type[this.teraType]}`) }); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.description`, { teraType: i18next.t(`modifierType:FormChangeItem.${Type[this.teraType]}`) }); + } + getPregenArgs(): any[] { return [ this.teraType ]; } } export class ContactHeldItemTransferChanceModifierType extends PokemonHeldItemModifierType { - constructor(name: string, chancePercent: integer, iconImage?: string, group?: string, soundName?: string) { - super(name, `Upon attacking, there is a ${chancePercent}% chance the foe's held item will be stolen.`, (type, args) => new Modifiers.ContactHeldItemTransferChanceModifier(type, (args[0] as Pokemon).id, chancePercent), iconImage, group, soundName); + private chancePercent: integer; + + constructor(localeKey: string, iconImage: string, chancePercent: integer, group?: string, soundName?: string) { + super(localeKey, iconImage, (type, args) => new Modifiers.ContactHeldItemTransferChanceModifier(type, (args[0] as Pokemon).id, chancePercent), group, soundName); + + this.chancePercent = chancePercent; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.ContactHeldItemTransferChanceModifierType.description`, { chancePercent: this.chancePercent }); } } export class TurnHeldItemTransferModifierType extends PokemonHeldItemModifierType { - constructor(name: string, iconImage?: string, group?: string, soundName?: string) { - super(name, 'Every turn, the holder acquires one held item from the foe.', (type, args) => new Modifiers.TurnHeldItemTransferModifier(type, (args[0] as Pokemon).id), iconImage, group, soundName); + constructor(localeKey: string, iconImage: string, group?: string, soundName?: string) { + super(localeKey, iconImage, (type, args) => new Modifiers.TurnHeldItemTransferModifier(type, (args[0] as Pokemon).id), group, soundName); + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.TurnHeldItemTransferModifierType.description`); } } export class EnemyAttackStatusEffectChanceModifierType extends ModifierType { - constructor(name: string, chancePercent: integer, effect: StatusEffect, iconImage?: string) { - super(name, `Adds a ${chancePercent}% chance to inflict ${getStatusEffectDescriptor(effect)} with attack moves`, (type, args) => new Modifiers.EnemyAttackStatusEffectChanceModifier(type, effect, chancePercent), iconImage, 'enemy_status_chance') + private chancePercent: integer; + private effect: StatusEffect; + + constructor(localeKey: string, iconImage: string, chancePercent: integer, effect: StatusEffect) { + super(localeKey, iconImage, (type, args) => new Modifiers.EnemyAttackStatusEffectChanceModifier(type, effect, chancePercent), 'enemy_status_chance') + + this.chancePercent = chancePercent; + this.effect = effect; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.EnemyAttackStatusEffectChanceModifierType.description`, { + chancePercent: this.chancePercent, + statusEffect: getStatusEffectDescriptor(this.effect), + }); } } export class EnemyEndureChanceModifierType extends ModifierType { - constructor(name: string, chancePercent: number, iconImage?: string) { - super(name, `Adds a ${chancePercent}% chance of enduring a hit`, (type, _args) => new Modifiers.EnemyEndureChanceModifier(type, chancePercent), iconImage, 'enemy_endure'); + private chancePercent: number; + + constructor(localeKey: string, iconImage: string, chancePercent: number) { + super(localeKey, iconImage, (type, _args) => new Modifiers.EnemyEndureChanceModifier(type, chancePercent), 'enemy_endure'); + + this.chancePercent = chancePercent; + } + + getDescription(scene: BattleScene): string { + return i18next.t(`modifierType:ModifierType.EnemyEndureChanceModifierType.description`, { chancePercent: this.chancePercent }); } } @@ -767,57 +988,56 @@ class WeightedModifierType { } export const modifierTypes = { - POKEBALL: () => new AddPokeballModifierType(PokeballType.POKEBALL, 5, 'pb'), - GREAT_BALL: () => new AddPokeballModifierType(PokeballType.GREAT_BALL, 5, 'gb'), - ULTRA_BALL: () => new AddPokeballModifierType(PokeballType.ULTRA_BALL, 5, 'ub'), - ROGUE_BALL: () => new AddPokeballModifierType(PokeballType.ROGUE_BALL, 5, 'rb'), - MASTER_BALL: () => new AddPokeballModifierType(PokeballType.MASTER_BALL, 1, 'mb'), + POKEBALL: () => new AddPokeballModifierType('pb', PokeballType.POKEBALL, 5), + GREAT_BALL: () => new AddPokeballModifierType('gb', PokeballType.GREAT_BALL, 5), + ULTRA_BALL: () => new AddPokeballModifierType('ub', PokeballType.ULTRA_BALL, 5), + ROGUE_BALL: () => new AddPokeballModifierType('rb', PokeballType.ROGUE_BALL, 5), + MASTER_BALL: () => new AddPokeballModifierType('mb', PokeballType.MASTER_BALL, 1), - RARE_CANDY: () => new PokemonLevelIncrementModifierType('Rare Candy'), - RARER_CANDY: () => new AllPokemonLevelIncrementModifierType('Rarer Candy'), + RARE_CANDY: () => new PokemonLevelIncrementModifierType(`modifierType:ModifierType.RARE_CANDY`, 'rare_candy'), + RARER_CANDY: () => new AllPokemonLevelIncrementModifierType(`modifierType:ModifierType.RARER_CANDY`, 'rarer_candy'), EVOLUTION_ITEM: () => new EvolutionItemModifierTypeGenerator(false), RARE_EVOLUTION_ITEM: () => new EvolutionItemModifierTypeGenerator(true), FORM_CHANGE_ITEM: () => new FormChangeItemModifierTypeGenerator(), - MEGA_BRACELET: () => new ModifierType('Mega Bracelet', 'Mega Stones become available.', (type, _args) => new Modifiers.MegaEvolutionAccessModifier(type)), - DYNAMAX_BAND: () => new ModifierType('Dynamax Band', 'Max Mushrooms become available.', (type, _args) => new Modifiers.GigantamaxAccessModifier(type)), - TERA_ORB: () => new ModifierType('Tera Orb', 'Tera Shards become available.', (type, _args) => new Modifiers.TerastallizeAccessModifier(type)), + MEGA_BRACELET: () => new ModifierType(`modifierType:ModifierType.MEGA_BRACELET`, 'mega_bracelet', (type, _args) => new Modifiers.MegaEvolutionAccessModifier(type)), + DYNAMAX_BAND: () => new ModifierType(`modifierType:ModifierType.DYNAMAX_BAND`, 'dynamax_band', (type, _args) => new Modifiers.GigantamaxAccessModifier(type)), + TERA_ORB: () => new ModifierType(`modifierType:ModifierType.TERA_ORB`, 'tera_orb', (type, _args) => new Modifiers.TerastallizeAccessModifier(type)), - MAP: () => new ModifierType('Map', 'Allows you to choose your destination at a crossroads', (type, _args) => new Modifiers.MapModifier(type)), + MAP: () => new ModifierType(`modifierType:ModifierType.MAP`, 'map', (type, _args) => new Modifiers.MapModifier(type)), - POTION: () => new PokemonHpRestoreModifierType('Potion', 20, 10), - SUPER_POTION: () => new PokemonHpRestoreModifierType('Super Potion', 50, 25), - HYPER_POTION: () => new PokemonHpRestoreModifierType('Hyper Potion', 200, 50), - MAX_POTION: () => new PokemonHpRestoreModifierType('Max Potion', 0, 100), - FULL_RESTORE: () => new PokemonHpRestoreModifierType('Full Restore', 0, 100, true), + POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.POTION`, 'potion', 20, 10), + SUPER_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.SUPER_POTION`, 'super_potion', 50, 25), + HYPER_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.HYPER_POTION`, 'hyper_potion', 200, 50), + MAX_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.MAX_POTION`, 'max_potion', 0, 100), + FULL_RESTORE: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.FULL_RESTORE`, 'full_restore', 0, 100), - REVIVE: () => new PokemonReviveModifierType('Revive', 50), - MAX_REVIVE: () => new PokemonReviveModifierType('Max Revive', 100), + REVIVE: () => new PokemonReviveModifierType(`modifierType:ModifierType.REVIVE`, 'revive', 50), + MAX_REVIVE: () => new PokemonReviveModifierType(`modifierType:ModifierType.MAX_REVIVE`, 'max_revive', 100), - FULL_HEAL: () => new PokemonStatusHealModifierType('Full Heal'), + FULL_HEAL: () => new PokemonStatusHealModifierType(`modifierType:ModifierType.FULL_HEAL`, 'full_heal'), - SACRED_ASH: () => new AllPokemonFullReviveModifierType('Sacred Ash'), + SACRED_ASH: () => new AllPokemonFullReviveModifierType(`modifierType:ModifierType.SACRED_ASH`, 'sacred_ash'), - REVIVER_SEED: () => new PokemonHeldItemModifierType('Reviver Seed', 'Revives the holder for 1/2 HP upon fainting', - (type, args) => new Modifiers.PokemonInstantReviveModifier(type, (args[0] as Pokemon).id)), + REVIVER_SEED: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.REVIVER_SEED`, 'reviver_seed', (type, args) => new Modifiers.PokemonInstantReviveModifier(type, (args[0] as Pokemon).id)), - ETHER: () => new PokemonPpRestoreModifierType('Ether', 10), - MAX_ETHER: () => new PokemonPpRestoreModifierType('Max Ether', -1), + ETHER: () => new PokemonPpRestoreModifierType(`modifierType:ModifierType.ETHER`, 'ether', 10), + MAX_ETHER: () => new PokemonPpRestoreModifierType(`modifierType:ModifierType.MAX_ETHER`, 'max_ether', -1), - ELIXIR: () => new PokemonAllMovePpRestoreModifierType('Elixir', 10), - MAX_ELIXIR: () => new PokemonAllMovePpRestoreModifierType('Max Elixir', -1), + ELIXIR: () => new PokemonAllMovePpRestoreModifierType(`modifierType:ModifierType.ELIXIR`, 'elixir', 10), + MAX_ELIXIR: () => new PokemonAllMovePpRestoreModifierType(`modifierType:ModifierType.MAX_ELIXIR`, 'max_elixir', -1), - PP_UP: () => new PokemonPpUpModifierType('PP Up', 1), - PP_MAX: () => new PokemonPpUpModifierType('PP Max', 3), + PP_UP: () => new PokemonPpUpModifierType(`modifierType:ModifierType.PP_UP`, 'pp_up', 1), + PP_MAX: () => new PokemonPpUpModifierType(`modifierType:ModifierType.PP_MAX`, 'pp_max', 3), /*REPEL: () => new DoubleBattleChanceBoosterModifierType('Repel', 5), SUPER_REPEL: () => new DoubleBattleChanceBoosterModifierType('Super Repel', 10), MAX_REPEL: () => new DoubleBattleChanceBoosterModifierType('Max Repel', 25),*/ - LURE: () => new DoubleBattleChanceBoosterModifierType('Lure', 5), - SUPER_LURE: () => new DoubleBattleChanceBoosterModifierType('Super Lure', 10), - MAX_LURE: () => new DoubleBattleChanceBoosterModifierType('Max Lure', 25), + LURE: () => new DoubleBattleChanceBoosterModifierType(`modifierType:ModifierType.LURE`, 'lure', 5), + SUPER_LURE: () => new DoubleBattleChanceBoosterModifierType(`modifierType:ModifierType.SUPER_LURE`, 'super_lure', 10), + MAX_LURE: () => new DoubleBattleChanceBoosterModifierType(`modifierType:ModifierType.MAX_LURE`, 'max_lure', 25), TEMP_STAT_BOOSTER: () => new ModifierTypeGenerator((party: Pokemon[], pregenArgs?: any[]) => { if (pregenArgs) @@ -879,94 +1099,82 @@ export const modifierTypes = { TM_GREAT: () => new TmModifierTypeGenerator(ModifierTier.GREAT), TM_ULTRA: () => new TmModifierTypeGenerator(ModifierTier.ULTRA), - MEMORY_MUSHROOM: () => new RememberMoveModifierType('Memory Mushroom', 'Recall one Pokémon\'s forgotten move', 'big_mushroom'), + MEMORY_MUSHROOM: () => new RememberMoveModifierType(`modifierType:ModifierType.MEMORY_MUSHROOM`, 'big_mushroom'), - EXP_SHARE: () => new ModifierType('EXP. All', 'Non-participants receive 20% of a single participant\'s EXP. Points.', - (type, _args) => new Modifiers.ExpShareModifier(type), 'exp_share'), - EXP_BALANCE: () => new ModifierType('EXP. Balance', 'Weighs EXP. Points received from battles towards lower-leveled party members', - (type, _args) => new Modifiers.ExpBalanceModifier(type)), + EXP_SHARE: () => new ModifierType(`modifierType:ModifierType.EXP_SHARE`, 'exp_share', (type, _args) => new Modifiers.ExpShareModifier(type), 'exp_share'), + EXP_BALANCE: () => new ModifierType(`modifierType:ModifierType.EXP_BALANCE`, 'exp_balance', (type, _args) => new Modifiers.ExpBalanceModifier(type)), - OVAL_CHARM: () => new ModifierType('Oval Charm', 'When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP.', - (type, _args) => new Modifiers.MultipleParticipantExpBonusModifier(type)), + OVAL_CHARM: () => new ModifierType(`modifierType:ModifierType.OVAL_CHARM`, 'oval_charm', (type, _args) => new Modifiers.MultipleParticipantExpBonusModifier(type)), - EXP_CHARM: () => new ExpBoosterModifierType('EXP. Charm', 25), - SUPER_EXP_CHARM: () => new ExpBoosterModifierType('Super EXP. Charm', 60), - GOLDEN_EXP_CHARM: () => new ExpBoosterModifierType('Golden EXP. Charm', 100), + EXP_CHARM: () => new ExpBoosterModifierType(`modifierType:ModifierType.EXP_CHARM`, 'exp_charm', 25), + SUPER_EXP_CHARM: () => new ExpBoosterModifierType(`modifierType:ModifierType.SUPER_EXP_CHARM`, 'super_exp_charm', 60), + GOLDEN_EXP_CHARM: () => new ExpBoosterModifierType(`modifierType:ModifierType.GOLDEN_EXP_CHARM`, 'golden_exp_charm', 100), - LUCKY_EGG: () => new PokemonExpBoosterModifierType('Lucky Egg', 40), - GOLDEN_EGG: () => new PokemonExpBoosterModifierType('Golden Egg', 100), + LUCKY_EGG: () => new PokemonExpBoosterModifierType(`modifierType:ModifierType.LUCKY_EGG`, 'lucky_egg', 40), + GOLDEN_EGG: () => new PokemonExpBoosterModifierType(`modifierType:ModifierType.GOLDEN_EGG`, 'golden_egg', 100), - SOOTHE_BELL: () => new PokemonFriendshipBoosterModifierType('Soothe Bell'), + SOOTHE_BELL: () => new PokemonFriendshipBoosterModifierType(`modifierType:ModifierType.SOOTHE_BELL`, 'soothe_bell'), - SOUL_DEW: () => new PokemonHeldItemModifierType('Soul Dew', 'Increases the influence of a Pokémon\'s nature on its stats by 10% (additive)', (type, args) => new Modifiers.PokemonNatureWeightModifier(type, (args[0] as Pokemon).id)), + SOUL_DEW: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.SOUL_DEW`, 'soul_dew', (type, args) => new Modifiers.PokemonNatureWeightModifier(type, (args[0] as Pokemon).id)), - NUGGET: () => new MoneyRewardModifierType('Nugget', 1, 'small'), - BIG_NUGGET: () => new MoneyRewardModifierType('Big Nugget', 2.5, 'moderate'), - RELIC_GOLD: () => new MoneyRewardModifierType('Relic Gold', 10, 'large'), + NUGGET: () => new MoneyRewardModifierType(`modifierType:ModifierType.NUGGET`, 'nugget', 1, `modifierType:ModifierType.MoneyRewardModifierType.extra.small`), + BIG_NUGGET: () => new MoneyRewardModifierType(`modifierType:ModifierType.BIG_NUGGET`, 'big_nugget', 2.5, `modifierType:ModifierType.MoneyRewardModifierType.extra.moderate`), + RELIC_GOLD: () => new MoneyRewardModifierType(`modifierType:ModifierType.RELIC_GOLD`, 'relic_gold', 10, `modifierType:ModifierType.MoneyRewardModifierType.extra.large`), - AMULET_COIN: () => new ModifierType('Amulet Coin', 'Increases money rewards by 20%', (type, _args) => new Modifiers.MoneyMultiplierModifier(type)), - GOLDEN_PUNCH: () => new PokemonHeldItemModifierType('Golden Punch', 'Grants 50% of damage inflicted as money', (type, args) => new Modifiers.DamageMoneyRewardModifier(type, (args[0] as Pokemon).id)), - COIN_CASE: () => new ModifierType('Coin Case', 'After every 10th battle, receive 10% of your money in interest.', (type, _args) => new Modifiers.MoneyInterestModifier(type)), + AMULET_COIN: () => new ModifierType(`modifierType:ModifierType.AMULET_COIN`, 'amulet_coin', (type, _args) => new Modifiers.MoneyMultiplierModifier(type)), + GOLDEN_PUNCH: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.GOLDEN_PUNCH`, 'golden_punch', (type, args) => new Modifiers.DamageMoneyRewardModifier(type, (args[0] as Pokemon).id)), + COIN_CASE: () => new ModifierType(`modifierType:ModifierType.COIN_CASE`, 'coin_case', (type, _args) => new Modifiers.MoneyInterestModifier(type)), - LOCK_CAPSULE: () => new ModifierType('Lock Capsule', 'Allows you to lock item rarities when rerolling items', (type, _args) => new Modifiers.LockModifierTiersModifier(type), 'lock_capsule'), + LOCK_CAPSULE: () => new ModifierType(`modifierType:ModifierType.LOCK_CAPSULE`, 'lock_capsule', (type, _args) => new Modifiers.LockModifierTiersModifier(type)), - GRIP_CLAW: () => new ContactHeldItemTransferChanceModifierType('Grip Claw', 10), - WIDE_LENS: () => new PokemonMoveAccuracyBoosterModifierType('Wide Lens', 5, 'wide_lens'), + GRIP_CLAW: () => new ContactHeldItemTransferChanceModifierType(`modifierType:ModifierType.GRIP_CLAW`, 'grip_claw', 10), + WIDE_LENS: () => new PokemonMoveAccuracyBoosterModifierType(`modifierType:ModifierType.WIDE_LENS`, 'wide_lens', 5), - MULTI_LENS: () => new PokemonMultiHitModifierType('Multi Lens', 'zoom_lens'), + MULTI_LENS: () => new PokemonMultiHitModifierType(`modifierType:ModifierType.MULTI_LENS`, 'zoom_lens'), - HEALING_CHARM: () => new ModifierType('Healing Charm', 'Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)', - (type, _args) => new Modifiers.HealingBoosterModifier(type, 1.1), 'healing_charm'), - CANDY_JAR: () => new ModifierType('Candy Jar', 'Increases the number of levels added by Rare Candy items by 1', (type, _args) => new Modifiers.LevelIncrementBoosterModifier(type)), + HEALING_CHARM: () => new ModifierType(`modifierType:ModifierType.HEALING_CHARM`, 'healing_charm', (type, _args) => new Modifiers.HealingBoosterModifier(type, 1.1)), + CANDY_JAR: () => new ModifierType(`modifierType:ModifierType.CANDY_JAR`, 'candy_jar', (type, _args) => new Modifiers.LevelIncrementBoosterModifier(type)), - BERRY_POUCH: () => new ModifierType('Berry Pouch', 'Adds a 25% chance that a used berry will not be consumed', - (type, _args) => new Modifiers.PreserveBerryModifier(type)), + BERRY_POUCH: () => new ModifierType(`modifierType:ModifierType.BERRY_POUCH`, 'berry_pouch', (type, _args) => new Modifiers.PreserveBerryModifier(type)), - FOCUS_BAND: () => new PokemonHeldItemModifierType('Focus Band', 'Adds a 10% chance to survive with 1 HP after being damaged enough to faint', - (type, args) => new Modifiers.SurviveDamageModifier(type, (args[0] as Pokemon).id)), + FOCUS_BAND: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.FOCUS_BAND`, 'focus_band', (type, args) => new Modifiers.SurviveDamageModifier(type, (args[0] as Pokemon).id)), - QUICK_CLAW: () => new PokemonHeldItemModifierType('Quick Claw', 'Adds a 10% chance to move first regardless of speed (after priority)', - (type, args) => new Modifiers.BypassSpeedChanceModifier(type, (args[0] as Pokemon).id)), + QUICK_CLAW: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.QUICK_CLAW`, 'quick_claw', (type, args) => new Modifiers.BypassSpeedChanceModifier(type, (args[0] as Pokemon).id)), - KINGS_ROCK: () => new PokemonHeldItemModifierType('King\'s Rock', 'Adds a 10% chance an attack move will cause the opponent to flinch', - (type, args) => new Modifiers.FlinchChanceModifier(type, (args[0] as Pokemon).id)), + KINGS_ROCK: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.KINGS_ROCK`, 'kings_rock', (type, args) => new Modifiers.FlinchChanceModifier(type, (args[0] as Pokemon).id)), - LEFTOVERS: () => new PokemonHeldItemModifierType('Leftovers', 'Heals 1/16 of a Pokémon\'s maximum HP every turn', - (type, args) => new Modifiers.TurnHealModifier(type, (args[0] as Pokemon).id)), - SHELL_BELL: () => new PokemonHeldItemModifierType('Shell Bell', 'Heals 1/8 of a Pokémon\'s dealt damage', - (type, args) => new Modifiers.HitHealModifier(type, (args[0] as Pokemon).id)), + LEFTOVERS: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.LEFTOVERS`, 'leftovers', (type, args) => new Modifiers.TurnHealModifier(type, (args[0] as Pokemon).id)), + SHELL_BELL: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.SHELL_BELL`, 'shell_bell', (type, args) => new Modifiers.HitHealModifier(type, (args[0] as Pokemon).id)), - BATON: () => new PokemonHeldItemModifierType('Baton', 'Allows passing along effects when switching Pokémon, which also bypasses traps', - (type, args) => new Modifiers.SwitchEffectTransferModifier(type, (args[0] as Pokemon).id), 'stick'), + BATON: () => new PokemonHeldItemModifierType(`modifierType:ModifierType.BATON`, 'stick', (type, args) => new Modifiers.SwitchEffectTransferModifier(type, (args[0] as Pokemon).id)), - SHINY_CHARM: () => new ModifierType('Shiny Charm', 'Dramatically increases the chance of a wild Pokémon being Shiny', (type, _args) => new Modifiers.ShinyRateBoosterModifier(type)), - ABILITY_CHARM: () => new ModifierType('Ability Charm', 'Dramatically increases the chance of a wild Pokémon having a Hidden Ability', (type, _args) => new Modifiers.HiddenAbilityRateBoosterModifier(type)), + SHINY_CHARM: () => new ModifierType(`modifierType:ModifierType.SHINY_CHARM`, 'shiny_charm', (type, _args) => new Modifiers.ShinyRateBoosterModifier(type)), + ABILITY_CHARM: () => new ModifierType(`modifierType:ModifierType.ABILITY_CHARM`, 'ability_charm', (type, _args) => new Modifiers.HiddenAbilityRateBoosterModifier(type)), - IV_SCANNER: () => new ModifierType('IV Scanner', 'Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first.', (type, _args) => new Modifiers.IvScannerModifier(type), 'scanner'), + IV_SCANNER: () => new ModifierType(`modifierType:ModifierType.IV_SCANNER`, 'scanner', (type, _args) => new Modifiers.IvScannerModifier(type)), - DNA_SPLICERS: () => new FusePokemonModifierType('DNA Splicers'), + DNA_SPLICERS: () => new FusePokemonModifierType(`modifierType:ModifierType.DNA_SPLICERS`, 'dna_splicers'), - MINI_BLACK_HOLE: () => new TurnHeldItemTransferModifierType('Mini Black Hole'), + MINI_BLACK_HOLE: () => new TurnHeldItemTransferModifierType(`modifierType:ModifierType.MINI_BLACK_HOLE`, 'mini_black_hole'), VOUCHER: () => new AddVoucherModifierType(VoucherType.REGULAR, 1), VOUCHER_PLUS: () => new AddVoucherModifierType(VoucherType.PLUS, 1), VOUCHER_PREMIUM: () => new AddVoucherModifierType(VoucherType.PREMIUM, 1), - GOLDEN_POKEBALL: () => new ModifierType(`Golden ${getPokeballName(PokeballType.POKEBALL)}`, 'Adds 1 extra item option at the end of every battle', - (type, _args) => new Modifiers.ExtraModifierModifier(type), 'pb_gold', null, 'pb_bounce_1'), + GOLDEN_POKEBALL: () => new ModifierType(`modifierType:ModifierType.GOLDEN_POKEBALL`, 'pb_gold', (type, _args) => new Modifiers.ExtraModifierModifier(type), null, 'pb_bounce_1'), - ENEMY_DAMAGE_BOOSTER: () => new ModifierType('Damage Token', 'Increases damage by 5%', (type, _args) => new Modifiers.EnemyDamageBoosterModifier(type, 5), 'wl_item_drop'), - ENEMY_DAMAGE_REDUCTION: () => new ModifierType('Protection Token', 'Reduces incoming damage by 2.5%', (type, _args) => new Modifiers.EnemyDamageReducerModifier(type, 2.5), 'wl_guard_spec'), + ENEMY_DAMAGE_BOOSTER: () => new ModifierType(`modifierType:ModifierType.ENEMY_DAMAGE_BOOSTER`, 'wl_item_drop', (type, _args) => new Modifiers.EnemyDamageBoosterModifier(type, 5)), + ENEMY_DAMAGE_REDUCTION: () => new ModifierType(`modifierType:ModifierType.ENEMY_DAMAGE_REDUCTION`, 'wl_guard_spec', (type, _args) => new Modifiers.EnemyDamageReducerModifier(type, 2.5)), //ENEMY_SUPER_EFFECT_BOOSTER: () => new ModifierType('Type Advantage Token', 'Increases damage of super effective attacks by 30%', (type, _args) => new Modifiers.EnemySuperEffectiveDamageBoosterModifier(type, 30), 'wl_custom_super_effective'), - ENEMY_HEAL: () => new ModifierType('Recovery Token', 'Heals 2% of max HP every turn', (type, _args) => new Modifiers.EnemyTurnHealModifier(type, 2), 'wl_potion'), - ENEMY_ATTACK_POISON_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType('Poison Token', 10, StatusEffect.POISON, 'wl_antidote'), - ENEMY_ATTACK_PARALYZE_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType('Paralyze Token', 10, StatusEffect.PARALYSIS, 'wl_paralyze_heal'), - ENEMY_ATTACK_SLEEP_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType('Sleep Token', 10, StatusEffect.SLEEP, 'wl_awakening'), - ENEMY_ATTACK_FREEZE_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType('Freeze Token', 10, StatusEffect.FREEZE, 'wl_ice_heal'), - ENEMY_ATTACK_BURN_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType('Burn Token', 10, StatusEffect.BURN, 'wl_burn_heal'), - ENEMY_STATUS_EFFECT_HEAL_CHANCE: () => new ModifierType('Full Heal Token', 'Adds a 10% chance every turn to heal a status condition', (type, _args) => new Modifiers.EnemyStatusEffectHealChanceModifier(type, 10), 'wl_full_heal'), - ENEMY_ENDURE_CHANCE: () => new EnemyEndureChanceModifierType('Endure Token', 2.5, 'wl_reset_urge'), - ENEMY_FUSED_CHANCE: () => new ModifierType('Fusion Token', 'Adds a 1% chance that a wild Pokémon will be a fusion', (type, _args) => new Modifiers.EnemyFusionChanceModifier(type, 1), 'wl_custom_spliced'), + ENEMY_HEAL: () => new ModifierType(`modifierType:ModifierType.ENEMY_HEAL`, 'wl_potion', (type, _args) => new Modifiers.EnemyTurnHealModifier(type, 2)), + ENEMY_ATTACK_POISON_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType(`modifierType:ModifierType.ENEMY_ATTACK_POISON_CHANCE`, 'wl_antidote', 10, StatusEffect.POISON), + ENEMY_ATTACK_PARALYZE_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType(`modifierType:ModifierType.ENEMY_ATTACK_PARALYZE_CHANCE`, 'wl_paralyze_heal', 10, StatusEffect.PARALYSIS), + ENEMY_ATTACK_SLEEP_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType(`modifierType:ModifierType.ENEMY_ATTACK_SLEEP_CHANCE`, 'wl_awakening', 10, StatusEffect.SLEEP), + ENEMY_ATTACK_FREEZE_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType(`modifierType:ModifierType.ENEMY_ATTACK_FREEZE_CHANCE`, 'wl_ice_heal', 10, StatusEffect.FREEZE), + ENEMY_ATTACK_BURN_CHANCE: () => new EnemyAttackStatusEffectChanceModifierType(`modifierType:ModifierType.ENEMY_ATTACK_BURN_CHANCE`, 'wl_burn_heal', 10, StatusEffect.BURN), + ENEMY_STATUS_EFFECT_HEAL_CHANCE: () => new ModifierType(`modifierType:ModifierType.ENEMY_STATUS_EFFECT_HEAL_CHANCE`, 'wl_full_heal', (type, _args) => new Modifiers.EnemyStatusEffectHealChanceModifier(type, 10)), + ENEMY_ENDURE_CHANCE: () => new EnemyEndureChanceModifierType(`modifierType:ModifierType.ENEMY_ENDURE_CHANCE`, 'wl_reset_urge', 2.5), + ENEMY_FUSED_CHANCE: () => new ModifierType(`modifierType:ModifierType.ENEMY_FUSED_CHANCE`, 'wl_custom_spliced', (type, _args) => new Modifiers.EnemyFusionChanceModifier(type, 1)), }; interface ModifierPool { diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index 44712b12778..b2d6fbf537a 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -31,6 +31,22 @@ export interface AbilityTranslationEntries { [key: string]: AbilityTranslationEntry } +export interface ModifierTypeTranslationEntry { + name?: string, + description?: string, + extra?: SimpleTranslationEntries +} + +export interface ModifierTypeTranslationEntries { + ModifierType: { [key: string]: ModifierTypeTranslationEntry }, + AttackTypeBoosterItem: SimpleTranslationEntries, + TempBattleStatBoosterItem: SimpleTranslationEntries, + BaseStatBoosterItem: SimpleTranslationEntries, + EvolutionItem: SimpleTranslationEntries, + FormChangeItem: SimpleTranslationEntries, + TeraType: SimpleTranslationEntries, +} + export interface Localizable { localize(): void; } @@ -111,6 +127,7 @@ declare module 'i18next' { nature: SimpleTranslationEntries; growth: SimpleTranslationEntries; weather: SimpleTranslationEntries; + modifierType: ModifierTypeTranslationEntries; }; } } From 5fa57d42a63cf606cd0133ce1b8bc514fdc46a00 Mon Sep 17 00:00:00 2001 From: FanHua Date: Thu, 16 May 2024 13:00:47 +0800 Subject: [PATCH 26/46] =?UTF-8?q?Fix=20the=20issue=20where=20=E2=80=98Tera?= =?UTF-8?q?stallizeModifierType=E2=80=99=20uses=20the=20wrong=20translatio?= =?UTF-8?q?n=20key.=20(#942)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/modifier/modifier-type.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index c0f33521b33..160043f2601 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -898,11 +898,11 @@ export class TerastallizeModifierType extends PokemonHeldItemModifierType implem } get name(): string { - return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.name`, { teraType: i18next.t(`modifierType:FormChangeItem.${Type[this.teraType]}`) }); + return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.name`, { teraType: i18next.t(`modifierType:TeraType.${Type[this.teraType]}`) }); } getDescription(scene: BattleScene): string { - return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.description`, { teraType: i18next.t(`modifierType:FormChangeItem.${Type[this.teraType]}`) }); + return i18next.t(`modifierType:ModifierType.TerastallizeModifierType.description`, { teraType: i18next.t(`modifierType:TeraType.${Type[this.teraType]}`) }); } getPregenArgs(): any[] { From b9d48e9138a3ae7a6534ee08edcbd3c76e114eab Mon Sep 17 00:00:00 2001 From: Ice <98368751+IceFire03@users.noreply.github.com> Date: Thu, 16 May 2024 00:12:19 -0500 Subject: [PATCH 27/46] Change seed flare stat drop to 2 stages (#943) --- src/data/move.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/data/move.ts b/src/data/move.ts index 46216eb754a..5f255d0fd51 100644 --- a/src/data/move.ts +++ b/src/data/move.ts @@ -5650,7 +5650,7 @@ export function initMoves() { .attr(StatusEffectAttr, StatusEffect.SLEEP) .target(MoveTarget.ALL_NEAR_ENEMIES), new AttackMove(Moves.SEED_FLARE, Type.GRASS, MoveCategory.SPECIAL, 120, 85, 5, 40, 0, 4) - .attr(StatChangeAttr, BattleStat.SPDEF, -1), + .attr(StatChangeAttr, BattleStat.SPDEF, -2), new AttackMove(Moves.OMINOUS_WIND, Type.GHOST, MoveCategory.SPECIAL, 60, 100, 5, 10, 0, 4) .attr(StatChangeAttr, [ BattleStat.ATK, BattleStat.DEF, BattleStat.SPATK, BattleStat.SPDEF, BattleStat.SPD ], 1, true) .windMove(), From b82b8c31d1d978ee88b30e394d95d75ace368ee1 Mon Sep 17 00:00:00 2001 From: FanHua Date: Thu, 16 May 2024 13:18:06 +0800 Subject: [PATCH 28/46] =?UTF-8?q?Fixed=20the=20incorrect=20translation=20k?= =?UTF-8?q?ey=20for=20=E2=80=98Never-Melt=20Ice=E2=80=99=20(#944)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Fixed the issue with the incorrect translation key for ‘Never-Melt Ice’ * fix typo --------- Co-authored-by: Benjamin Odom --- src/locales/de/modifier-type.ts | 2 +- src/locales/en/modifier-type.ts | 2 +- src/locales/es/modifier-type.ts | 2 +- src/locales/fr/modifier-type.ts | 2 +- src/locales/it/modifier-type.ts | 2 +- src/locales/pt_BR/modifier-type.ts | 2 +- src/locales/zh_CN/modifier-type.ts | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/locales/de/modifier-type.ts b/src/locales/de/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/de/modifier-type.ts +++ b/src/locales/de/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/en/modifier-type.ts b/src/locales/en/modifier-type.ts index 729644dc3b8..a8e43d20883 100644 --- a/src/locales/en/modifier-type.ts +++ b/src/locales/en/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_nelt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/es/modifier-type.ts b/src/locales/es/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/es/modifier-type.ts +++ b/src/locales/es/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/fr/modifier-type.ts b/src/locales/fr/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/fr/modifier-type.ts +++ b/src/locales/fr/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/it/modifier-type.ts b/src/locales/it/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/it/modifier-type.ts +++ b/src/locales/it/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/pt_BR/modifier-type.ts b/src/locales/pt_BR/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/pt_BR/modifier-type.ts +++ b/src/locales/pt_BR/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", diff --git a/src/locales/zh_CN/modifier-type.ts b/src/locales/zh_CN/modifier-type.ts index 729644dc3b8..043d7a705d5 100644 --- a/src/locales/zh_CN/modifier-type.ts +++ b/src/locales/zh_CN/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never-nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", From fff2eda127c898dc8c816bf996437648fa4190f0 Mon Sep 17 00:00:00 2001 From: Madmadness65 Date: Thu, 16 May 2024 00:26:27 -0500 Subject: [PATCH 29/46] Add additional form change entries for Terapagos It still can't switch from it's Terastal form to Stellar form yet, but this is in preparation for it. --- src/data/pokemon-forms.ts | 4 +++- src/locales/en/modifier-type.ts | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/src/data/pokemon-forms.ts b/src/data/pokemon-forms.ts index 9a38ed81e34..a8bc07e92df 100644 --- a/src/data/pokemon-forms.ts +++ b/src/data/pokemon-forms.ts @@ -705,7 +705,9 @@ export const pokemonFormChanges: PokemonFormChanges = { new SpeciesFormChange(Species.OGERPON, 'cornerstone-mask-tera', 'cornerstone-mask', new SpeciesFormChangeManualTrigger(), true) //When no longer holding a Rock Tera Shard ], [Species.TERAPAGOS]: [ - new SpeciesFormChange(Species.TERAPAGOS, '', 'terastal', new SpeciesFormChangeManualTrigger(), true) + new SpeciesFormChange(Species.TERAPAGOS, '', 'terastal', new SpeciesFormChangeManualTrigger(), true), + new SpeciesFormChange(Species.TERAPAGOS, 'terastal', 'stellar', new SpeciesFormChangeManualTrigger(), true), //When holding a Stellar Tera Shard + new SpeciesFormChange(Species.TERAPAGOS, 'stellar', 'terastal', new SpeciesFormChangeManualTrigger(), true) //When no longer holding a Stellar Tera Shard ], [Species.GALAR_DARMANITAN]: [ new SpeciesFormChange(Species.GALAR_DARMANITAN, '', 'zen', new SpeciesFormChangeManualTrigger(), true), diff --git a/src/locales/en/modifier-type.ts b/src/locales/en/modifier-type.ts index a8e43d20883..043d7a705d5 100644 --- a/src/locales/en/modifier-type.ts +++ b/src/locales/en/modifier-type.ts @@ -258,7 +258,7 @@ export const modifierType: ModifierTypeTranslationEntries = { "miracle_seed": "Miracle Seed", "magnet": "Magnet", "twisted_spoon": "Twisted Spoon", - "never_nelt_ice": "Never-Melt Ice", + "never_melt_ice": "Never-Melt Ice", "dragon_fang": "Dragon Fang", "black_glasses": "Black Glasses", "fairy_feather": "Fairy Feather", From 0aca9aed9c950a783c010a5913c7ee95dc8dbfaf Mon Sep 17 00:00:00 2001 From: FanHua Date: Thu, 16 May 2024 14:17:29 +0800 Subject: [PATCH 30/46] fix: FULL_RESTORE should now heal status (#947) --- src/modifier/modifier-type.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index 160043f2601..c87403d3d2f 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -1011,7 +1011,7 @@ export const modifierTypes = { SUPER_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.SUPER_POTION`, 'super_potion', 50, 25), HYPER_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.HYPER_POTION`, 'hyper_potion', 200, 50), MAX_POTION: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.MAX_POTION`, 'max_potion', 0, 100), - FULL_RESTORE: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.FULL_RESTORE`, 'full_restore', 0, 100), + FULL_RESTORE: () => new PokemonHpRestoreModifierType(`modifierType:ModifierType.FULL_RESTORE`, 'full_restore', 0, 100, true), REVIVE: () => new PokemonReviveModifierType(`modifierType:ModifierType.REVIVE`, 'revive', 50), MAX_REVIVE: () => new PokemonReviveModifierType(`modifierType:ModifierType.MAX_REVIVE`, 'max_revive', 100), From 77cfa580786cf6853da38cf307463ac45657e604 Mon Sep 17 00:00:00 2001 From: FanHua Date: Thu, 16 May 2024 14:49:07 +0800 Subject: [PATCH 31/46] fix: EXP_SHARE should not have a group parameter (#948) --- src/modifier/modifier-type.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index c87403d3d2f..50bf2f78a0c 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -1101,7 +1101,7 @@ export const modifierTypes = { MEMORY_MUSHROOM: () => new RememberMoveModifierType(`modifierType:ModifierType.MEMORY_MUSHROOM`, 'big_mushroom'), - EXP_SHARE: () => new ModifierType(`modifierType:ModifierType.EXP_SHARE`, 'exp_share', (type, _args) => new Modifiers.ExpShareModifier(type), 'exp_share'), + EXP_SHARE: () => new ModifierType(`modifierType:ModifierType.EXP_SHARE`, 'exp_share', (type, _args) => new Modifiers.ExpShareModifier(type)), EXP_BALANCE: () => new ModifierType(`modifierType:ModifierType.EXP_BALANCE`, 'exp_balance', (type, _args) => new Modifiers.ExpBalanceModifier(type)), OVAL_CHARM: () => new ModifierType(`modifierType:ModifierType.OVAL_CHARM`, 'oval_charm', (type, _args) => new Modifiers.MultipleParticipantExpBonusModifier(type)), From 8508ee7bc688c2ec530f83c12fd0837f1d0df3dc Mon Sep 17 00:00:00 2001 From: Benjamin Odom Date: Thu, 16 May 2024 02:05:36 -0500 Subject: [PATCH 32/46] Semi-Invulnerable Hit Checks Count as Miss (#904) Fixed an issue where targeting the user of a Semi-Invulnerable move caused the move to cancel. These moves now miss instead. No Guard and other accuracy locking moves still function as they were already duplicating their check in hitCheck. Fixed an issue where IGNORE_ACCURACY was checking against the current move for targets instead of Lock-On's target --- src/phases.ts | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/src/phases.ts b/src/phases.ts index e2755328c69..90039502c30 100644 --- a/src/phases.ts +++ b/src/phases.ts @@ -2270,12 +2270,8 @@ export class MovePhase extends BattlePhase { } const targets = this.scene.getField(true).filter(p => { - if (this.targets.indexOf(p.getBattlerIndex()) > -1) { - const hiddenTag = p.getTag(HiddenTag); - if (hiddenTag && !this.move.getMove().getAttrs(HitsTagAttr).filter(hta => (hta as HitsTagAttr).tagType === hiddenTag.tagType).length && !p.hasAbilityWithAttr(AlwaysHitAbAttr) && !this.pokemon.hasAbilityWithAttr(AlwaysHitAbAttr)) - return false; + if (this.targets.indexOf(p.getBattlerIndex()) > -1) return true; - } return false; }); @@ -2316,10 +2312,17 @@ export class MovePhase extends BattlePhase { if (this.move.moveId) this.showMoveText(); - if ((moveQueue.length && moveQueue[0].move === Moves.NONE) || (!targets.length && !this.move.getMove().getAttrs(SacrificialAttr).length)) { - moveQueue.shift(); + // This should only happen when there are no valid targets left on the field + if ((moveQueue.length && moveQueue[0].move === Moves.NONE) || !targets.length) { + this.showFailedText(); this.cancel(); + + // Record a failed move so Abilities like Truant don't trigger next turn and soft-lock this.pokemon.pushMoveHistory({ move: Moves.NONE, result: MoveResult.FAIL }); + + this.pokemon.lapseTags(BattlerTagLapseType.MOVE_EFFECT); // Remove any tags from moves like Fly/Dive/etc. + + moveQueue.shift(); return this.end(); } @@ -2590,13 +2593,14 @@ export class MoveEffectPhase extends PokemonPhase { if (user.hasAbilityWithAttr(AlwaysHitAbAttr) || target.hasAbilityWithAttr(AlwaysHitAbAttr)) return true; + // If the user should ignore accuracy on a target, check who the user targeted last turn and see if they match + if (user.getTag(BattlerTagType.IGNORE_ACCURACY) && (user.getLastXMoves().slice(1).find(() => true)?.targets || []).indexOf(target.getBattlerIndex()) !== -1) + return true; + const hiddenTag = target.getTag(HiddenTag); if (hiddenTag && !this.move.getMove().getAttrs(HitsTagAttr).filter(hta => (hta as HitsTagAttr).tagType === hiddenTag.tagType).length) return false; - if (user.getTag(BattlerTagType.IGNORE_ACCURACY) && (user.getLastXMoves().find(() => true)?.targets || []).indexOf(target.getBattlerIndex()) > -1) - return true; - const moveAccuracy = new Utils.NumberHolder(this.move.getMove().accuracy); applyMoveAttrs(VariableAccuracyAttr, user, target, this.move.getMove(), moveAccuracy); From b30f73fb7245aa4f4b4fbfae1448b281f218b0e1 Mon Sep 17 00:00:00 2001 From: Gerafique <155723753+Gerafique@users.noreply.github.com> Date: Thu, 16 May 2024 10:18:01 +0200 Subject: [PATCH 33/46] Update GER translations starter-select-ui-handler.ts (#952) added uncaught corrected ability --- src/locales/de/starter-select-ui-handler.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/locales/de/starter-select-ui-handler.ts b/src/locales/de/starter-select-ui-handler.ts index 5f6dae32cf6..0723c14ad82 100644 --- a/src/locales/de/starter-select-ui-handler.ts +++ b/src/locales/de/starter-select-ui-handler.ts @@ -17,7 +17,7 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "gen8": "VIII", "gen9": "IX", "growthRate": "Wachstum:", - "ability": "Fhgkeit:", + "ability": "Fähgkeit:", "passive": "Passiv:", "nature": "Wesen:", "eggMoves": "Ei-Attacken", @@ -40,5 +40,5 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "disablePassive": "Passiv-Skill deaktivieren", "locked": "Gesperrt", "disabled": "Deaktiviert", - "uncaught": "Uncaught" + "uncaught": "Ungefangen" } From 0365ca88264d34a1990ef90e009ed8cb78a4c389 Mon Sep 17 00:00:00 2001 From: Gerafique <155723753+Gerafique@users.noreply.github.com> Date: Thu, 16 May 2024 10:22:04 +0200 Subject: [PATCH 34/46] Added weather.ts GER translations (#953) added translations for each weather-type --- src/locales/de/weather.ts | 60 +++++++++++++++++++-------------------- 1 file changed, 30 insertions(+), 30 deletions(-) diff --git a/src/locales/de/weather.ts b/src/locales/de/weather.ts index 999613f1566..0c5635de736 100644 --- a/src/locales/de/weather.ts +++ b/src/locales/de/weather.ts @@ -4,41 +4,41 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; * The weather namespace holds text displayed when weather is active during a battle */ export const weather: SimpleTranslationEntries = { - "sunnyStartMessage": "The sunlight got bright!", - "sunnyLapseMessage": "The sunlight is strong.", - "sunnyClearMessage": "The sunlight faded.", + "sunnyStartMessage": "Die Sonne hellt auf!", + "sunnyLapseMessage": "Die Sonne blendet.", + "sunnyClearMessage": "Die Sonne schwächt ab.", - "rainStartMessage": "A downpour started!", - "rainLapseMessage": "The downpour continues.", - "rainClearMessage": "The rain stopped.", + "rainStartMessage": "Es fängt an zu regnen!", + "rainLapseMessage": "Es regnet weiterhin.", + "rainClearMessage": "Es hört auf zu regnen.", - "sandstormStartMessage": "A sandstorm brewed!", - "sandstormLapseMessage": "The sandstorm rages.", - "sandstormClearMessage": "The sandstorm subsided.", - "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + "sandstormStartMessage": "Ein Sandsturm braut sich zusammen!", + "sandstormLapseMessage": "Der Sandsturm tobt.", + "sandstormClearMessage": "Der Sandsturm lässt nach.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} ist vom\nSandsturm beeinträchtigt!", - "hailStartMessage": "It started to hail!", - "hailLapseMessage": "Hail continues to fall.", - "hailClearMessage": "The hail stopped.", - "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + "hailStartMessage": "Es fängt an zu hageln!", + "hailLapseMessage": "Es hagelt weiterhin.", + "hailClearMessage": "Es hört auf zu hageln.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} ist vom\nHagel beeinträchtigt!", - "snowStartMessage": "It started to snow!", - "snowLapseMessage": "The snow is falling down.", - "snowClearMessage": "The snow stopped.", + "snowStartMessage": "Es fängt an zu schneien!", + "snowLapseMessage": "Es schneit weiterhin.", + "snowClearMessage": "Es hört auf zu schneien.", - "fogStartMessage": "A thick fog emerged!", - "fogLapseMessage": "The fog continues.", - "fogClearMessage": "The fog disappeared.", + "fogStartMessage": "Es fängt an zu nebeln!", + "fogLapseMessage": "Es nebelt weiterhin.", + "fogClearMessage": "Es hört auf zu nebeln.", - "heavyRainStartMessage": "A heavy downpour started!", - "heavyRainLapseMessage": "The heavy downpour continues.", - "heavyRainClearMessage": "The heavy rain stopped.", + "heavyRainStartMessage": "Ein Starkregen beginnt!", + "heavyRainLapseMessage": "Der Starkregen hält an.", + "heavyRainClearMessage": "Der Starkregen lässt nach.", - "harshSunStartMessage": "The sunlight got hot!", - "harshSunLapseMessage": "The sun is scorching hot.", - "harshSunClearMessage": "The harsh sunlight faded.", + "harshSunStartMessage": "Das Sonnenlicht wird wärmer!", + "harshSunLapseMessage": "Das Sonnenlicht brennt.", + "harshSunClearMessage": "Das Sonnenlicht schwächt ab.", - "strongWindsStartMessage": "A heavy wind began!", - "strongWindsLapseMessage": "The wind blows intensely.", - "strongWindsClearMessage": "The heavy wind stopped." -} \ No newline at end of file + "strongWindsStartMessage": "Ein starker Wind zieht auf!", + "strongWindsLapseMessage": "Der starke Wind tobt.", + "strongWindsClearMessage": "Der starke Wind legt sich." +} From 482accda18c0af93cd58784d329e200e792684bd Mon Sep 17 00:00:00 2001 From: Jannik Tappert <38758606+CodeTappert@users.noreply.github.com> Date: Thu, 16 May 2024 10:23:47 +0200 Subject: [PATCH 35/46] Added german modifier-type.ts localization (#949) * Added german modifier-type.ts * Fixed Text that was to long and added missing formatting * Fixed a key that was wrong * Changed never_melt_ice again. Now it the same as in other languages --- src/locales/de/modifier-type.ts | 539 ++++++++++++++++---------------- 1 file changed, 270 insertions(+), 269 deletions(-) diff --git a/src/locales/de/modifier-type.ts b/src/locales/de/modifier-type.ts index 043d7a705d5..dea1421ac20 100644 --- a/src/locales/de/modifier-type.ts +++ b/src/locales/de/modifier-type.ts @@ -4,406 +4,407 @@ export const modifierType: ModifierTypeTranslationEntries = { ModifierType: { "AddPokeballModifierType": { name: "{{modifierCount}}x {{pokeballName}}", - description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + description: "Erhalte {{pokeballName}} x{{modifierCount}} (Inventar: {{pokeballAmount}}) \nFangrate: {{catchRate}}", }, "AddVoucherModifierType": { name: "{{modifierCount}}x {{voucherTypeName}}", - description: "Receive {{voucherTypeName}} x{{modifierCount}}", + description: "Erhalte {{voucherTypeName}} x{{modifierCount}}", }, "PokemonHeldItemModifierType": { extra: { - "inoperable": "{{pokemonName}} can't take\nthis item!", - "tooMany": "{{pokemonName}} has too many\nof this item!", + "inoperable": "{{pokemonName}} kann dieses\nItem nicht nehmen!", + "tooMany": "{{pokemonName}} hat zu viele\nvon diesem Item!", } }, "PokemonHpRestoreModifierType": { - description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + description: "Füllt {{restorePoints}} KP oder {{restorePercent}}% der KP für ein Pokémon auf. Je nachdem, welcher Wert höher ist", extra: { - "fully": "Fully restores HP for one Pokémon", - "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + "fully": "Füllt die KP eines Pokémon wieder vollständig auf.", + "fullyWithStatus": "Füllt die KP eines Pokémon wieder vollständig auf und behebt alle Statusprobleme", } }, "PokemonReviveModifierType": { - description: "Revives one Pokémon and restores {{restorePercent}}% HP", + description: "Belebt ein kampunfähiges Pokémon wieder und stellt {{restorePercent}}% KP wieder her", }, "PokemonStatusHealModifierType": { - description: "Heals any status ailment for one Pokémon", + description: "Behebt alle Statusprobleme eines Pokémon", }, "PokemonPpRestoreModifierType": { - description: "Restores {{restorePoints}} PP for one Pokémon move", + description: "Füllt {{restorePoints}} AP der ausgewählten Attacke eines Pokémon auf", extra: { - "fully": "Restores all PP for one Pokémon move", + "fully": "Füllt alle AP der ausgewählten Attacke eines Pokémon auf", } }, "PokemonAllMovePpRestoreModifierType": { - description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + description: "Stellt {{restorePoints}} AP für alle Attacken eines Pokémon auf", extra: { - "fully": "Restores all PP for all of one Pokémon's moves", + "fully": "Füllt alle AP für alle Attacken eines Pokémon auf", } }, "PokemonPpUpModifierType": { - description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + description: "Erhöht die maximale Anzahl der AP der ausgewählten Attacke um {{upPoints}} für jede 5 maximale AP (maximal 3)", }, "PokemonNatureChangeModifierType": { - name: "{{natureName}} Mint", - description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + name: "{{natureName}} Minze", + description: "Ändert das Wesen zu {{natureName}}. Schaltet dieses Wesen permanent für diesen Starter frei.", }, "DoubleBattleChanceBoosterModifierType": { - description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + description: "Verdoppelt die Wahrscheinlichkeit, dass die nächsten {{battleCount}} Begegnungen mit wilden Pokémon ein Doppelkampf sind.", }, "TempBattleStatBoosterModifierType": { - description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + description: "Erhöht die {{tempBattleStatName}} aller Teammitglieder für 5 Kämpfe um eine Stufe", }, "AttackTypeBoosterModifierType": { - description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + description: "Erhöht die Stärke aller {{moveType}}attacken eines Pokémon um 20%", }, "PokemonLevelIncrementModifierType": { - description: "Increases a Pokémon's level by 1", + description: "Erhöht das Level eines Pokémon um 1", }, "AllPokemonLevelIncrementModifierType": { - description: "Increases all party members' level by 1", + description: "Erhöht das Level aller Teammitglieder um 1", }, "PokemonBaseStatBoosterModifierType": { - description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + description: "Erhöht den {{statName}} Basiswert des Trägers um 10%. Das Stapellimit erhöht sich, je höher dein IS-Wert ist.", }, "AllPokemonFullHpRestoreModifierType": { - description: "Restores 100% HP for all Pokémon", + description: "Stellt 100% der KP aller Pokémon her", }, "AllPokemonFullReviveModifierType": { - description: "Revives all fainted Pokémon, fully restoring HP", + description: "Belebt alle kampunfähigen Pokémon wieder und stellt ihre KP vollständig wieder her", }, "MoneyRewardModifierType": { - description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + description:"Gewährt einen {{moneyMultiplier}} Geldbetrag von (₽{{moneyAmount}})", extra: { - "small": "small", - "moderate": "moderate", - "large": "large", + "small": "kleinen", + "moderate": "moderaten", + "large": "großen", }, }, "ExpBoosterModifierType": { - description: "Increases gain of EXP. Points by {{boostPercent}}%", + description: "Erhöht die erhaltenen Erfahrungspunkte um {{boostPercent}}%", }, "PokemonExpBoosterModifierType": { - description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + description: "Erhöht die Menge der erhaltenen Erfahrungspunkte für den Träger um {{boostPercent}}%", }, "PokemonFriendshipBoosterModifierType": { - description: "Increases friendship gain per victory by 50%", + description: "Erhöht den Freundschaftszuwachs pro Sieg um 50%.", }, "PokemonMoveAccuracyBoosterModifierType": { - description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + description: "Erhöht die Genauigkeit der Angriffe um {{accuracyAmount}} (maximal 100)", }, "PokemonMultiHitModifierType": { - description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + description: "Attacken treffen ein weiteres mal mit einer Reduktion von 60/75/82,5% der Stärke", }, "TmModifierType": { name: "TM{{moveId}} - {{moveName}}", - description: "Teach {{moveName}} to a Pokémon", + description: "Bringt einem Pokémon {{moveName}} bei", }, "EvolutionItemModifierType": { - description: "Causes certain Pokémon to evolve", + description: "Erlaubt es bestimmten Pokémon sich zu entwickeln", }, "FormChangeItemModifierType": { - description: "Causes certain Pokémon to change form", + description: "Erlaubt es bestimmten Pokémon ihre Form zu ändern", }, "FusePokemonModifierType": { - description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + description: "Fusioniert zwei Pokémon (überträgt die Fähigkeit, teilt Basiswerte und Typ auf, gemeinsamer Attackenpool)", }, "TerastallizeModifierType": { - name: "{{teraType}} Tera Shard", - description: "{{teraType}} Terastallizes the holder for up to 10 battles", + name: "{{teraType}} Terra-Stück", + description: "{{teraType}} Terakristallisiert den Träger für bis zu 10 Kämpfe", }, "ContactHeldItemTransferChanceModifierType": { - description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + description:"Beim Angriff besteht eine {{chancePercent}}%ige Chance, dass das getragene Item des Gegners gestohlen wird." }, "TurnHeldItemTransferModifierType": { - description: "Every turn, the holder acquires one held item from the foe", + description: "Jede Runde erhält der Träger ein getragenes Item des Gegners", }, "EnemyAttackStatusEffectChanceModifierType": { - description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + description: "Fügt Angriffen eine {{chancePercent}}%ige Chance hinzu, {{statusEffect}} zu verursachen", }, "EnemyEndureChanceModifierType": { - description: "Adds a {{chancePercent}}% chance of enduring a hit", + description: "Gibt den Träger eine {{chancePercent}}%ige Chance, einen Angriff zu überleben", }, - "RARE_CANDY": { name: "Rare Candy" }, - "RARER_CANDY": { name: "Rarer Candy" }, + "RARE_CANDY": { name: "Sonderbonbon" }, + "RARER_CANDY": { name: "Supersondererbonbon" }, - "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, - "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, - "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + "MEGA_BRACELET": { name: "Mega-Armband", description: "Mega-Steine werden verfügbar" }, + "DYNAMAX_BAND": { name: "Dynamax-Band", description: "Dyna-Pilze werden verfügbar" }, + "TERA_ORB": { name: "Terakristall-Orb", description: "Tera-Stücke werden verfügbar" }, - "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + "MAP": { name: "Karte", description: "Ermöglicht es dir, an einer Kreuzung dein Ziel zu wählen." }, - "POTION": { name: "Potion" }, - "SUPER_POTION": { name: "Super Potion" }, - "HYPER_POTION": { name: "Hyper Potion" }, - "MAX_POTION": { name: "Max Potion" }, - "FULL_RESTORE": { name: "Full Restore" }, - - "REVIVE": { name: "Revive" }, - "MAX_REVIVE": { name: "Max Revive" }, - - "FULL_HEAL": { name: "Full Heal" }, + "POTION": { name: "Trank" }, + "SUPER_POTION": { name: "Supertrank" }, + "HYPER_POTION": { name: "Hypertrank" }, + "MAX_POTION": { name: "Top-Trank" }, + "FULL_RESTORE": { name: "Top-Genesung" }, - "SACRED_ASH": { name: "Sacred Ash" }, + "REVIVE": { name: "Beleber" }, + "MAX_REVIVE": { name: "Top-Beleber" }, - "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + "FULL_HEAL": { name: "Hyperheiler" }, - "ETHER": { name: "Ether" }, - "MAX_ETHER": { name: "Max Ether" }, + "SACRED_ASH": { name: "Zauberasche" }, + + "REVIVER_SEED": { name: "Belebersamen", description: "Belebt den Träger mit der Hälfte seiner KP wieder sollte er kampfunfähig werden" }, + + "ETHER": { name: "Äther" }, + "MAX_ETHER": { name: "Top-Äther" }, "ELIXIR": { name: "Elixir" }, - "MAX_ELIXIR": { name: "Max Elixir" }, + "MAX_ELIXIR": { name: "Top-Elixir" }, - "PP_UP": { name: "PP Up" }, - "PP_MAX": { name: "PP Max" }, + "PP_UP": { name: "AP-Plus" }, + "PP_MAX": { name: "AP-Top" }, - "LURE": { name: "Lure" }, - "SUPER_LURE": { name: "Super Lure" }, - "MAX_LURE": { name: "Max Lure" }, + "LURE": { name: "Lockparfüm" }, + "SUPER_LURE": { name: "Super-Lockparfüm" }, + "MAX_LURE": { name: "Top-Lockparfüm" }, - "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + "MEMORY_MUSHROOM": { name: "Erinnerungspilz", description: "Lässt ein Pokémon eine vergessene Attacke wiedererlernen" }, - "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, - "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + "EXP_SHARE": { name: "EP-Teiler", description: "Pokémon, die nicht am Kampf teilgenommen haben, bekommen 20% der Erfahrungspunkte eines Kampfteilnehmers" }, + "EXP_BALANCE": { name: "EP-Ausgleicher", description: "Gewichtet die in Kämpfen erhaltenen Erfahrungspunkte auf niedrigstufigere Gruppenmitglieder." }, - "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + "OVAL_CHARM": { name: "Ovalpin", description: "Wenn mehrere Pokémon am Kampf teilnehmen, erhählt jeder von ihnen 10% extra Erfahrungspunkte" }, - "EXP_CHARM": { name: "EXP. Charm" }, - "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, - "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + "EXP_CHARM": { name: "EP-Pin" }, + "SUPER_EXP_CHARM": { name: "Super-EP-Pin" }, + "GOLDEN_EXP_CHARM": { name: "Goldener EP-Pin" }, - "LUCKY_EGG": { name: "Lucky Egg" }, - "GOLDEN_EGG": { name: "Golden Egg" }, + "LUCKY_EGG": { name: "Glücks-Ei" }, + "GOLDEN_EGG": { name: "Goldenes Ei" }, - "SOOTHE_BELL": { name: "Soothe Bell" }, + "SOOTHE_BELL": { name: "Sanftglocke" }, - "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + "SOUL_DEW": { name: "Seelentau", description: "Erhöht den Einfluss des Wesens eines Pokemon auf seine Werte um 10% (additiv)" }, "NUGGET": { name: "Nugget" }, - "BIG_NUGGET": { name: "Big Nugget" }, - "RELIC_GOLD": { name: "Relic Gold" }, + "BIG_NUGGET": { name: "Riesennugget" }, + "RELIC_GOLD": { name: "Alter Dukat" }, - "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, - "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, - "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, - - "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + "AMULET_COIN": { name: "Münzamulett", description: "Erhöht das Preisgeld um 20%" }, + "GOLDEN_PUNCH": { name: "Goldschlag", description: "Gewährt Geld in Höhe von 50% des zugefügten Schadens" }, + "COIN_CASE": { name: "Münzkorb", description: "Erhalte nach jedem 10ten Kampf 10% Zinsen auf dein Geld" }, - "GRIP_CLAW": { name: "Grip Claw" }, - "WIDE_LENS": { name: "Wide Lens" }, - - "MULTI_LENS": { name: "Multi Lens" }, + "LOCK_CAPSULE": { name: "Tresorkapsel", description: "Erlaubt es die Seltenheitsstufe der Items festzusetzen wenn diese neu gerollt werden" }, - "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, - "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + "GRIP_CLAW": { name: "Griffklaue" }, + "WIDE_LENS": { name: "Großlinse" }, - "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + "MULTI_LENS": { name: "Mehrfachlinse" }, - "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + "HEALING_CHARM": { name: "Heilungspin", description: "Erhöht die Effektivität von Heilungsattacken sowie Heilitems um 10% (Beleber ausgenommen)" }, + "CANDY_JAR": { name: "Bonbonglas", description: "Erhöht die Anzahl der Level die ein Sonderbonbon erhöht um 1" }, - "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + "BERRY_POUCH": { name: "Beerentüte", description: "Fügt eine 25% Chance hinzu, dass Beeren nicht verbraucht werden" }, - "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + "FOCUS_BAND": { name: "Fokusband", description: "Fügt eine 10% Chance hinzu, dass Angriffe die zur Kampfunfähigkeit führen mit 1 KP überlebt werden" }, - "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, - "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + "QUICK_CLAW": { name: "Quick Claw", description: "Fügt eine 10% Change hinzu als erster anzugreifen. (Nach Prioritätsangriffen)" }, - "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + "KINGS_ROCK": { name: "King-Stein", description: "Fügt eine 10% Chance hinzu, dass der Gegner nach einem Angriff zurückschreckt" }, - "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, - "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + "LEFTOVERS": { name: "Überreste", description: "Heilt 1/16 der maximalen KP eines Pokémon pro Runde" }, + "SHELL_BELL": { name: "Muschelglocke", description: "Heilt den Anwender um 1/8 des von ihm zugefügten Schadens" }, - "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + "BATON": { name: "Stab", description: "Ermöglicht das Weitergeben von Effekten beim Wechseln von Pokémon, wodurch auch Fallen umgangen werden." }, - "DNA_SPLICERS": { name: "DNA Splicers" }, + "SHINY_CHARM": { name: "Schillerpin", description: "Erhöht die Chance deutlich, dass ein wildes Pokémon ein schillernd ist" }, + "ABILITY_CHARM": { name: "Ability Charm", description: "Erhöht die Chance deutlich, dass ein wildes Pokémon eine versteckte Fähigkeit hat" }, - "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + "IV_SCANNER": { name: "IS-Scanner", description: "Erlaubt es die IS-Werte von wilden Pokémon zu scannen.\n(2 IS-Werte pro Staplung. Die besten IS-Werte zuerst)" }, - "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + "DNA_SPLICERS": { name: "DNS-Keil" }, + + "MINI_BLACK_HOLE": { name: "Mini schwarzes Loch" }, + + "GOLDEN_POKEBALL": { name: "Goldener Pokéball", description: "Fügt eine zusätzliche Item-Auswahlmöglichkeit nach jedem Kampf hinzu" }, + + "ENEMY_DAMAGE_BOOSTER": { name: "Schadensmarke", description: "Erhöht den Schaden um 5%" }, + "ENEMY_DAMAGE_REDUCTION": { name: "Schutzmarke", description: "Verringert den erhaltenen Schaden um 2,5%" }, + "ENEMY_HEAL": { name: "Wiederherstellungsmarke", description: "Heilt 2% der maximalen KP pro Runde" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "Giftmarke" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { "name": "Lähmungsmarke" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { "name": "Schlafmarke" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { "name": "Gefriermarke" }, + "ENEMY_ATTACK_BURN_CHANCE": { "name": "Brandmarke" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { "name": "Vollheilungsmarke", "description": "Fügt eine 10%ige Chance hinzu, jede Runde einen Statuszustand zu heilen" }, + "ENEMY_ENDURE_CHANCE": { "name": "Ausdauer-Marke" }, + "ENEMY_FUSED_CHANCE": { "name": "Fusionsmarke", "description": "Fügt eine 1%ige Chance hinzu, dass ein wildes Pokémon eine Fusion ist" }, - "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, - "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, - "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, - "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, - "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, - "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, - "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, - "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, - "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, - "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, - "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, }, TempBattleStatBoosterItem: { - "x_attack": "X Attack", - "x_defense": "X Defense", - "x_sp_atk": "X Sp. Atk", - "x_sp_def": "X Sp. Def", - "x_speed": "X Speed", - "x_accuracy": "X Accuracy", - "dire_hit": "Dire Hit", + "x_attack": "X-Angriff", + "x_defense": "X-Verteidigung", + "x_sp_atk": "X-Sp.-Ang.", + "x_sp_def": "X-Sp.-Vert.", + "x_speed": "X-Tempo", + "x_accuracy": "X-Treffer", + "dire_hit": "X-Volltreffer", }, AttackTypeBoosterItem: { - "silk_scarf": "Silk Scarf", - "black_belt": "Black Belt", - "sharp_beak": "Sharp Beak", - "poison_barb": "Poison Barb", - "soft_sand": "Soft Sand", - "hard_stone": "Hard Stone", - "silver_powder": "Silver Powder", - "spell_tag": "Spell Tag", - "metal_coat": "Metal Coat", - "charcoal": "Charcoal", - "mystic_water": "Mystic Water", - "miracle_seed": "Miracle Seed", + "silk_scarf": "Seidenschal", + "black_belt": "Schwarzgurt", + "sharp_beak": "Spitzer Schnabel", + "poison_barb": "Giftstich", + "soft_sand": "Pudersand", + "hard_stone": "Granitstein", + "silver_powder": "Silberstaub", + "spell_tag": "Bannsticker", + "metal_coat": "Metallmantel", + "charcoal": "Holzkohle", + "mystic_water": "Zauberwasser", + "miracle_seed": "Wundersaat", "magnet": "Magnet", - "twisted_spoon": "Twisted Spoon", - "never_melt_ice": "Never-Melt Ice", - "dragon_fang": "Dragon Fang", - "black_glasses": "Black Glasses", - "fairy_feather": "Fairy Feather", + "twisted_spoon": "Krümmlöffel", + "never_melt_ice": "Ewiges Eis", + "dragon_fang": "Drachenzahn", + "black_glasses": "Schattenbrille", + "fairy_feather": "Feendaune", }, BaseStatBoosterItem: { - "hp_up": "HP Up", + "hp_up": "KP-Plus", "protein": "Protein", - "iron": "Iron", - "calcium": "Calcium", - "zinc": "Zinc", - "carbos": "Carbos", + "iron": "Eisen", + "calcium": "Kalzium", + "zinc": "Zink", + "carbos": "Carbon", }, EvolutionItem: { - "NONE": "None", + "NONE": "Keins", - "LINKING_CORD": "Linking Cord", - "SUN_STONE": "Sun Stone", - "MOON_STONE": "Moon Stone", - "LEAF_STONE": "Leaf Stone", - "FIRE_STONE": "Fire Stone", - "WATER_STONE": "Water Stone", - "THUNDER_STONE": "Thunder Stone", - "ICE_STONE": "Ice Stone", - "DUSK_STONE": "Dusk Stone", - "DAWN_STONE": "Dawn Stone", - "SHINY_STONE": "Shiny Stone", - "CRACKED_POT": "Cracked Pot", - "SWEET_APPLE": "Sweet Apple", - "TART_APPLE": "Tart Apple", - "STRAWBERRY_SWEET": "Strawberry Sweet", - "UNREMARKABLE_TEACUP": "Unremarkable Teacup", - - "CHIPPED_POT": "Chipped Pot", - "BLACK_AUGURITE": "Black Augurite", - "GALARICA_CUFF": "Galarica Cuff", - "GALARICA_WREATH": "Galarica Wreath", - "PEAT_BLOCK": "Peat Block", - "AUSPICIOUS_ARMOR": "Auspicious Armor", - "MALICIOUS_ARMOR": "Malicious Armor", - "MASTERPIECE_TEACUP": "Masterpiece Teacup", - "METAL_ALLOY": "Metal Alloy", - "SCROLL_OF_DARKNESS": "Scroll Of Darkness", - "SCROLL_OF_WATERS": "Scroll Of Waters", - "SYRUPY_APPLE": "Syrupy Apple", + "LINKING_CORD": "Linkkabel", + "SUN_STONE": "Sonnenstein", + "MOON_STONE": "Mondstein", + "LEAF_STONE": "Blattstein", + "FIRE_STONE": "Feuerstein", + "WATER_STONE": "Wasserstein", + "THUNDER_STONE": "Donnerstein", + "ICE_STONE": "Eisstein", + "DUSK_STONE": "Finsterstein", + "DAWN_STONE": "Funkelstein", + "SHINY_STONE": "Leuchtstein", + "CRACKED_POT": "Rissige Kanne", + "SWEET_APPLE": "Süßer Apfel", + "TART_APPLE": "Saurer Apfel", + "STRAWBERRY_SWEET": "Zucker-Erdbeere", + "UNREMARKABLE_TEACUP": "Simple Teeschale", + + "CHIPPED_POT": "Löchrige Kanne", + "BLACK_AUGURITE": "Schwarzaugit", + "GALARICA_CUFF": "Galarnuss-Reif", + "GALARICA_WREATH": "Galarnuss-Kranz", + "PEAT_BLOCK": "Torfblock", + "AUSPICIOUS_ARMOR": "Glorienrüstung", + "MALICIOUS_ARMOR": "Fluchrüstung", + "MASTERPIECE_TEACUP": "Edle Teeschale", + "METAL_ALLOY": "Legierungsmetall", + "SCROLL_OF_DARKNESS": "Unlicht-Schriftrolle", + "SCROLL_OF_WATERS": "Wasser-Schriftrolle", + "SYRUPY_APPLE": "Saftiger Apfel", }, FormChangeItem: { - "NONE": "None", + "NONE": "Keins", - "ABOMASITE": "Abomasite", - "ABSOLITE": "Absolite", - "AERODACTYLITE": "Aerodactylite", - "AGGRONITE": "Aggronite", - "ALAKAZITE": "Alakazite", - "ALTARIANITE": "Altarianite", - "AMPHAROSITE": "Ampharosite", - "AUDINITE": "Audinite", - "BANETTITE": "Banettite", - "BEEDRILLITE": "Beedrillite", - "BLASTOISINITE": "Blastoisinite", - "BLAZIKENITE": "Blazikenite", - "CAMERUPTITE": "Cameruptite", - "CHARIZARDITE_X": "Charizardite X", - "CHARIZARDITE_Y": "Charizardite Y", - "DIANCITE": "Diancite", - "GALLADITE": "Galladite", - "GARCHOMPITE": "Garchompite", - "GARDEVOIRITE": "Gardevoirite", - "GENGARITE": "Gengarite", - "GLALITITE": "Glalitite", - "GYARADOSITE": "Gyaradosite", - "HERACRONITE": "Heracronite", - "HOUNDOOMINITE": "Houndoominite", - "KANGASKHANITE": "Kangaskhanite", - "LATIASITE": "Latiasite", - "LATIOSITE": "Latiosite", - "LOPUNNITE": "Lopunnite", - "LUCARIONITE": "Lucarionite", - "MANECTITE": "Manectite", - "MAWILITE": "Mawilite", - "MEDICHAMITE": "Medichamite", - "METAGROSSITE": "Metagrossite", - "MEWTWONITE_X": "Mewtwonite X", - "MEWTWONITE_Y": "Mewtwonite Y", - "PIDGEOTITE": "Pidgeotite", - "PINSIRITE": "Pinsirite", - "RAYQUAZITE": "Rayquazite", - "SABLENITE": "Sablenite", - "SALAMENCITE": "Salamencite", - "SCEPTILITE": "Sceptilite", - "SCIZORITE": "Scizorite", - "SHARPEDONITE": "Sharpedonite", - "SLOWBRONITE": "Slowbronite", - "STEELIXITE": "Steelixite", - "SWAMPERTITE": "Swampertite", - "TYRANITARITE": "Tyranitarite", - "VENUSAURITE": "Venusaurite", + "ABOMASITE": "Rexblisarnit", + "ABSOLITE": "Absolnit", + "AERODACTYLITE": "Aerodactylonit", + "AGGRONITE": "Stollossnit", + "ALAKAZITE": "Simsalanit", + "ALTARIANITE": "Altarianit", + "AMPHAROSITE": "Ampharosnit", + "AUDINITE": "Ohrdochnit", + "BANETTITE": "Banetteonit", + "BEEDRILLITE": "Bibornit", + "BLASTOISINITE": "Turtoknit", + "BLAZIKENITE": "Lohgocknit", + "CAMERUPTITE": "Cameruptnit", + "CHARIZARDITE_X": "Gluraknit X", + "CHARIZARDITE_Y": "Gluraknit Y", + "DIANCITE": "Diancienit", + "GALLADITE": "Galagladinit", + "GARCHOMPITE": "Knakracknit", + "GARDEVOIRITE": "Guardevoirnit", + "GENGARITE": "Gengarnit ", + "GLALITITE": "Firnontornit", + "GYARADOSITE": "Garadosnit", + "HERACRONITE": "Skarabornit", + "HOUNDOOMINITE": "Hundemonit ", + "KANGASKHANITE": "Kangamanit", + "LATIASITE": "Latiasnit", + "LATIOSITE": "Latiosnit", + "LOPUNNITE": "Schlapornit", + "LUCARIONITE": "Lucarionit", + "MANECTITE": "Voltensonit", + "MAWILITE": "Flunkifernit", + "MEDICHAMITE": "Meditalisnit", + "METAGROSSITE": "Metagrossnit", + "MEWTWONITE_X": "Mewtunit X", + "MEWTWONITE_Y": "Mewtunit Y", + "PIDGEOTITE": "Taubossnit", + "PINSIRITE": "Pinsirnit", + "RAYQUAZITE": "Rayquazanit", + "SABLENITE": "Zobirisnit", + "SALAMENCITE": "Brutalandanit", + "SCEPTILITE": "Gewaldronit", + "SCIZORITE": "Scheroxnit", + "SHARPEDONITE": "Tohaidonit", + "SLOWBRONITE": "Lahmusnit", + "STEELIXITE": "Stahlosnit", + "SWAMPERTITE": "Sumpexnit", + "TYRANITARITE": "Despotarnit", + "VENUSAURITE": "Bisaflornit", - "BLUE_ORB": "Blue Orb", - "RED_ORB": "Red Orb", - "SHARP_METEORITE": "Sharp Meteorite", - "HARD_METEORITE": "Hard Meteorite", - "SMOOTH_METEORITE": "Smooth Meteorite", - "ADAMANT_CRYSTAL": "Adamant Crystal", - "LUSTROUS_ORB": "Lustrous Orb", - "GRISEOUS_CORE": "Griseous Core", - "REVEAL_GLASS": "Reveal Glass", + "BLUE_ORB": "Blauer Edelstein", + "RED_ORB": "Roter Edelstein", + "SHARP_METEORITE": "Scharfer Meteorit", + "HARD_METEORITE": "Harter Meteorit", + "SMOOTH_METEORITE": "Glatter Meteorit", + "ADAMANT_CRYSTAL": "Adamantkristall", + "LUSTROUS_ORB": "Weiß-Orb", + "GRISEOUS_CORE": "Platinumkristall", + "REVEAL_GLASS": "Wahrspiegel", "GRACIDEA": "Gracidea", - "MAX_MUSHROOMS": "Max Mushrooms", - "DARK_STONE": "Dark Stone", - "LIGHT_STONE": "Light Stone", - "PRISON_BOTTLE": "Prison Bottle", - "N_LUNARIZER": "N Lunarizer", - "N_SOLARIZER": "N Solarizer", - "RUSTED_SWORD": "Rusted Sword", - "RUSTED_SHIELD": "Rusted Shield", - "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", - "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", - "WELLSPRING_MASK": "Wellspring Mask", - "HEARTHFLAME_MASK": "Hearthflame Mask", - "CORNERSTONE_MASK": "Cornerstone Mask", - "SHOCK_DRIVE": "Shock Drive", - "BURN_DRIVE": "Burn Drive", - "CHILL_DRIVE": "Chill Drive", - "DOUSE_DRIVE": "Douse Drive", + "MAX_MUSHROOMS": "Dyna-Pilz", + "DARK_STONE": "Dunkelstein", + "LIGHT_STONE": "Lichtstein", + "PRISON_BOTTLE": "Banngefäß", + "N_LUNARIZER": "Necrolun", + "N_SOLARIZER": "Necrosol", + "RUSTED_SWORD": "Rostiges Schwert", + "RUSTED_SHIELD": "Rostiges Schild", + "ICY_REINS_OF_UNITY": "eisige Zügel des Bundes", + "SHADOW_REINS_OF_UNITY": "schattige Zügel des Bundes", + "WELLSPRING_MASK": "Brunnenmaske", + "HEARTHFLAME_MASK": "Ofenmaske", + "CORNERSTONE_MASK": "Fundamentmaske", + "SHOCK_DRIVE": "Blitzmodul", + "BURN_DRIVE": "Flammenmodul", + "CHILL_DRIVE": "Gefriermodul", + "DOUSE_DRIVE": "Aquamodul", }, TeraType: { - "UNKNOWN": "Unknown", + "UNKNOWN": "Unbekannt", "NORMAL": "Normal", - "FIGHTING": "Fighting", - "FLYING": "Flying", - "POISON": "Poison", - "GROUND": "Ground", - "ROCK": "Rock", - "BUG": "Bug", - "GHOST": "Ghost", - "STEEL": "Steel", - "FIRE": "Fire", - "WATER": "Water", - "GRASS": "Grass", - "ELECTRIC": "Electric", - "PSYCHIC": "Psychic", - "ICE": "Ice", - "DRAGON": "Dragon", - "DARK": "Dark", - "FAIRY": "Fairy", + "FIGHTING": "Kampf", + "FLYING": "Flug", + "POISON": "Gift", + "GROUND": "Boden", + "ROCK": "Gestein", + "BUG": "Käfer", + "GHOST": "Geist", + "STEEL": "Stahl", + "FIRE": "Feuer", + "WATER": "Wasser", + "GRASS": "Pflanze", + "ELECTRIC": "Elektro", + "PSYCHIC": "Psycho", + "ICE": "Eis", + "DRAGON": "Drache", + "DARK": "Unlicht", + "FAIRY": "Fee", "STELLAR": "Stellar", }, } as const; \ No newline at end of file From 975d1ed5626354e89999bd1420f2669cbe87724a Mon Sep 17 00:00:00 2001 From: Valentin Porchet Date: Thu, 16 May 2024 10:31:50 +0200 Subject: [PATCH 36/46] feat: added localisation for eggs and french translations (#403) * feat: added localisation for eggs and french translations * fixes on french translations after review --------- Co-authored-by: Madmadness65 <59298170+Madmadness65@users.noreply.github.com> Co-authored-by: Benjamin Odom --- src/data/egg.ts | 23 ++++++++-------- src/locales/de/config.ts | 2 ++ src/locales/de/egg.ts | 21 ++++++++++++++ src/locales/en/config.ts | 2 ++ src/locales/en/egg.ts | 21 ++++++++++++++ src/locales/es/config.ts | 2 ++ src/locales/es/egg.ts | 21 ++++++++++++++ src/locales/fr/config.ts | 2 ++ src/locales/fr/egg.ts | 21 ++++++++++++++ src/locales/it/config.ts | 2 ++ src/locales/it/egg.ts | 21 ++++++++++++++ src/plugins/i18n.ts | 1 + src/ui/egg-gacha-ui-handler.ts | 50 ++++++++++++++++++++++++---------- src/ui/egg-list-ui-handler.ts | 3 +- 14 files changed, 165 insertions(+), 27 deletions(-) create mode 100644 src/locales/de/egg.ts create mode 100644 src/locales/en/egg.ts create mode 100644 src/locales/es/egg.ts create mode 100644 src/locales/fr/egg.ts create mode 100644 src/locales/it/egg.ts diff --git a/src/data/egg.ts b/src/data/egg.ts index 41216f27ee7..6437dfce262 100644 --- a/src/data/egg.ts +++ b/src/data/egg.ts @@ -4,6 +4,7 @@ import BattleScene from "../battle-scene"; import { Species } from "./enums/species"; import { getPokemonSpecies, speciesStarters } from "./pokemon-species"; import { EggTier } from "./enums/egg-type"; +import i18next from '../plugins/i18n'; export const EGG_SEED = 1073741824; @@ -56,34 +57,34 @@ export function getEggDescriptor(egg: Egg): string { return 'Manaphy'; switch (egg.tier) { case EggTier.GREAT: - return 'Rare'; + return i18next.t('egg:greatTier'); case EggTier.ULTRA: - return 'Epic'; + return i18next.t('egg:ultraTier'); case EggTier.MASTER: - return 'Legendary'; + return i18next.t('egg:masterTier'); default: - return 'Common'; + return i18next.t('egg:defaultTier'); } } export function getEggHatchWavesMessage(hatchWaves: integer): string { if (hatchWaves <= 5) - return 'Sounds can be heard coming from inside! It will hatch soon!'; + return i18next.t('egg:hatchWavesMessageSoon'); if (hatchWaves <= 15) - return 'It appears to move occasionally. It may be close to hatching.'; + return i18next.t('egg:hatchWavesMessageClose'); if (hatchWaves <= 50) - return 'What will hatch from this? It doesn\'t seem close to hatching.'; - return 'It looks like this Egg will take a long time to hatch.'; + return i18next.t('egg:hatchWavesMessageNotClose'); + return i18next.t('egg:hatchWavesMessageLongTime'); } export function getEggGachaTypeDescriptor(scene: BattleScene, egg: Egg): string { switch (egg.gachaType) { case GachaType.LEGENDARY: - return `Legendary Rate Up (${getPokemonSpecies(getLegendaryGachaSpeciesForTimestamp(scene, egg.timestamp)).getName()})`; + return `${i18next.t('egg:gachaTypeLegendary')} (${getPokemonSpecies(getLegendaryGachaSpeciesForTimestamp(scene, egg.timestamp)).getName()})`; case GachaType.MOVE: - return 'Rare Egg Move Rate Up'; + return i18next.t('egg:gachaTypeMove'); case GachaType.SHINY: - return 'Shiny Rate Up'; + return i18next.t('egg:gachaTypeShiny'); } } diff --git a/src/locales/de/config.ts b/src/locales/de/config.ts index 04ad328b6ec..7c8b455ef3d 100644 --- a/src/locales/de/config.ts +++ b/src/locales/de/config.ts @@ -2,6 +2,7 @@ import { ability } from "./ability"; import { abilityTriggers } from "./ability-trigger"; import { battle } from "./battle"; import { commandUiHandler } from "./command-ui-handler"; +import { egg } from "./egg"; import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; @@ -21,6 +22,7 @@ export const deConfig = { abilityTriggers: abilityTriggers, battle: battle, commandUiHandler: commandUiHandler, + egg: egg, fightUiHandler: fightUiHandler, menuUiHandler: menuUiHandler, menu: menu, diff --git a/src/locales/de/egg.ts b/src/locales/de/egg.ts new file mode 100644 index 00000000000..358c1b4a503 --- /dev/null +++ b/src/locales/de/egg.ts @@ -0,0 +1,21 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const egg: SimpleTranslationEntries = { + "egg": "Egg", + "greatTier": "Rare", + "ultraTier": "Epic", + "masterTier": "Legendary", + "defaultTier": "Common", + "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", + "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", + "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", + "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", + "gachaTypeLegendary": "Legendary Rate Up", + "gachaTypeMove": "Rare Egg Move Rate Up", + "gachaTypeShiny": "Shiny Rate Up", + "selectMachine": "Select a machine.", + "notEnoughVouchers": "You don't have enough vouchers!", + "tooManyEggs": "You have too many eggs!", + "pull": "Pull", + "pulls": "Pulls" +} as const; \ No newline at end of file diff --git a/src/locales/en/config.ts b/src/locales/en/config.ts index 0b3fd1505cc..f6b385fe433 100644 --- a/src/locales/en/config.ts +++ b/src/locales/en/config.ts @@ -2,6 +2,7 @@ import { ability } from "./ability"; import { abilityTriggers } from "./ability-trigger"; import { battle } from "./battle"; import { commandUiHandler } from "./command-ui-handler"; +import { egg } from "./egg"; import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; @@ -22,6 +23,7 @@ export const enConfig = { abilityTriggers: abilityTriggers, battle: battle, commandUiHandler: commandUiHandler, + egg: egg, fightUiHandler: fightUiHandler, menuUiHandler: menuUiHandler, menu: menu, diff --git a/src/locales/en/egg.ts b/src/locales/en/egg.ts new file mode 100644 index 00000000000..358c1b4a503 --- /dev/null +++ b/src/locales/en/egg.ts @@ -0,0 +1,21 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const egg: SimpleTranslationEntries = { + "egg": "Egg", + "greatTier": "Rare", + "ultraTier": "Epic", + "masterTier": "Legendary", + "defaultTier": "Common", + "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", + "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", + "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", + "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", + "gachaTypeLegendary": "Legendary Rate Up", + "gachaTypeMove": "Rare Egg Move Rate Up", + "gachaTypeShiny": "Shiny Rate Up", + "selectMachine": "Select a machine.", + "notEnoughVouchers": "You don't have enough vouchers!", + "tooManyEggs": "You have too many eggs!", + "pull": "Pull", + "pulls": "Pulls" +} as const; \ No newline at end of file diff --git a/src/locales/es/config.ts b/src/locales/es/config.ts index b38ae994c38..84a05233616 100644 --- a/src/locales/es/config.ts +++ b/src/locales/es/config.ts @@ -2,6 +2,7 @@ import { ability } from "./ability"; import { abilityTriggers } from "./ability-trigger"; import { battle } from "./battle"; import { commandUiHandler } from "./command-ui-handler"; +import { egg } from "./egg"; import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; @@ -22,6 +23,7 @@ export const esConfig = { abilityTriggers: abilityTriggers, battle: battle, commandUiHandler: commandUiHandler, + egg: egg, fightUiHandler: fightUiHandler, menuUiHandler: menuUiHandler, menu: menu, diff --git a/src/locales/es/egg.ts b/src/locales/es/egg.ts new file mode 100644 index 00000000000..358c1b4a503 --- /dev/null +++ b/src/locales/es/egg.ts @@ -0,0 +1,21 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const egg: SimpleTranslationEntries = { + "egg": "Egg", + "greatTier": "Rare", + "ultraTier": "Epic", + "masterTier": "Legendary", + "defaultTier": "Common", + "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", + "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", + "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", + "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", + "gachaTypeLegendary": "Legendary Rate Up", + "gachaTypeMove": "Rare Egg Move Rate Up", + "gachaTypeShiny": "Shiny Rate Up", + "selectMachine": "Select a machine.", + "notEnoughVouchers": "You don't have enough vouchers!", + "tooManyEggs": "You have too many eggs!", + "pull": "Pull", + "pulls": "Pulls" +} as const; \ No newline at end of file diff --git a/src/locales/fr/config.ts b/src/locales/fr/config.ts index 5ff44b46d31..84c20a957ed 100644 --- a/src/locales/fr/config.ts +++ b/src/locales/fr/config.ts @@ -2,6 +2,7 @@ import { ability } from "./ability"; import { abilityTriggers } from "./ability-trigger"; import { battle } from "./battle"; import { commandUiHandler } from "./command-ui-handler"; +import { egg } from "./egg"; import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; @@ -22,6 +23,7 @@ export const frConfig = { abilityTriggers: abilityTriggers, battle: battle, commandUiHandler: commandUiHandler, + egg: egg, fightUiHandler: fightUiHandler, menuUiHandler: menuUiHandler, menu: menu, diff --git a/src/locales/fr/egg.ts b/src/locales/fr/egg.ts new file mode 100644 index 00000000000..566e423b69f --- /dev/null +++ b/src/locales/fr/egg.ts @@ -0,0 +1,21 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const egg: SimpleTranslationEntries = { + "egg": "Œuf", + "greatTier": "Rare", + "ultraTier": "Épique", + "masterTier": "Légendaire", + "defaultTier": "Commun", + "hatchWavesMessageSoon": "Il fait du bruit. Il va éclore !", + "hatchWavesMessageClose": "Il bouge de temps en temps. Il devrait bientôt éclore.", + "hatchWavesMessageNotClose": "Qu’est-ce qui va en sortir ? Ça va mettre du temps.", + "hatchWavesMessageLongTime": "Cet Œuf va sûrement mettre du temps à éclore.", + "gachaTypeLegendary": "Taux de Légendaires élevé", + "gachaTypeMove": "Taux de Capacité Œuf Rare élevé", + "gachaTypeShiny": "Taux de Chromatiques élevé", + "selectMachine": "Sélectionnez une machine.", + "notEnoughVouchers": "Vous n’avez pas assez de coupons !", + "tooManyEggs": "Vous avez trop d’Œufs !", + "pull": "Tirage", + "pulls": "Tirages" +} as const; \ No newline at end of file diff --git a/src/locales/it/config.ts b/src/locales/it/config.ts index d81143bf577..0247a7e0f80 100644 --- a/src/locales/it/config.ts +++ b/src/locales/it/config.ts @@ -2,6 +2,7 @@ import { ability } from "./ability"; import { abilityTriggers } from "./ability-trigger"; import { battle } from "./battle"; import { commandUiHandler } from "./command-ui-handler"; +import { egg } from "./egg"; import { fightUiHandler } from "./fight-ui-handler"; import { growth } from "./growth"; import { menu } from "./menu"; @@ -22,6 +23,7 @@ export const itConfig = { abilityTriggers: abilityTriggers, battle: battle, commandUiHandler: commandUiHandler, + egg: egg, fightUiHandler: fightUiHandler, menuUiHandler: menuUiHandler, menu: menu, diff --git a/src/locales/it/egg.ts b/src/locales/it/egg.ts new file mode 100644 index 00000000000..358c1b4a503 --- /dev/null +++ b/src/locales/it/egg.ts @@ -0,0 +1,21 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const egg: SimpleTranslationEntries = { + "egg": "Egg", + "greatTier": "Rare", + "ultraTier": "Epic", + "masterTier": "Legendary", + "defaultTier": "Common", + "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", + "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", + "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", + "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", + "gachaTypeLegendary": "Legendary Rate Up", + "gachaTypeMove": "Rare Egg Move Rate Up", + "gachaTypeShiny": "Shiny Rate Up", + "selectMachine": "Select a machine.", + "notEnoughVouchers": "You don't have enough vouchers!", + "tooManyEggs": "You have too many eggs!", + "pull": "Pull", + "pulls": "Pulls" +} as const; \ No newline at end of file diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index b2d6fbf537a..ffd45317121 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -126,6 +126,7 @@ declare module 'i18next' { starterSelectUiHandler: SimpleTranslationEntries; nature: SimpleTranslationEntries; growth: SimpleTranslationEntries; + egg: SimpleTranslationEntries; weather: SimpleTranslationEntries; modifierType: ModifierTypeTranslationEntries; }; diff --git a/src/ui/egg-gacha-ui-handler.ts b/src/ui/egg-gacha-ui-handler.ts index a7fd61b3040..7fd49157da7 100644 --- a/src/ui/egg-gacha-ui-handler.ts +++ b/src/ui/egg-gacha-ui-handler.ts @@ -10,8 +10,7 @@ import { addWindow } from "./ui-theme"; import { Tutorial, handleTutorial } from "../tutorial"; import { EggTier } from "../data/enums/egg-type"; import {Button} from "../enums/buttons"; - -const defaultText = 'Select a machine.'; +import i18next from '../plugins/i18n'; export default class EggGachaUiHandler extends MessageUiHandler { private eggGachaContainer: Phaser.GameObjects.Container; @@ -33,6 +32,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { private cursorObj: Phaser.GameObjects.Image; private transitioning: boolean; private transitionCancelled: boolean; + private defaultText: string; constructor(scene: BattleScene) { super(scene, Mode.EGG_GACHA); @@ -43,6 +43,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { this.gachaInfoContainers = []; this.voucherCountLabels = []; + this.defaultText = i18next.t('egg:selectMachine'); } setup() { @@ -151,8 +152,27 @@ export default class EggGachaUiHandler extends MessageUiHandler { this.eggGachaOptionSelectBg.setOrigin(1, 1); this.eggGachaOptionsContainer.add(this.eggGachaOptionSelectBg); - const optionText = addTextObject(this.scene, 0, 0, ' x1 1 Pull\n x10 10 Pulls\n x1 5 Pulls\n x1 10 Pulls\n x1 25 Pulls\nCancel', TextStyle.WINDOW); - optionText.setLineSpacing(12); + const pullOptions = [ + { multiplier: 'x1', description: `1 ${i18next.t('egg:pull')}` }, + { multiplier: 'x10', description: `10 ${i18next.t('egg:pulls')}` }, + { multiplier: 'x1', description: `5 ${i18next.t('egg:pulls')}` }, + { multiplier: 'x1', description: `10 ${i18next.t('egg:pulls')}` }, + { multiplier: 'x1', description: `25 ${i18next.t('egg:pulls')}` } + ]; + + const pullOptionsText = pullOptions.map(option => ` ${option.multiplier.padEnd(4)} ${option.description}`).join('\n'); + + const optionText = addTextObject( + this.scene, + 0, + 0, + `${pullOptionsText}\n${i18next.t('menu:cancel')}`, + TextStyle.WINDOW, + ); + + optionText.setLineSpacing(28); + optionText.setFontSize('80px'); + this.eggGachaOptionsContainer.add(optionText); optionText.setPositionRelative(this.eggGachaOptionSelectBg, 16, 9); @@ -223,7 +243,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { show(args: any[]): boolean { super.show(args); - this.getUi().showText(defaultText, 0); + this.getUi().showText(this.defaultText, 0); this.setGachaCursor(1); @@ -474,7 +494,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { showText(text: string, delay?: number, callback?: Function, callbackDelay?: number, prompt?: boolean, promptDelay?: number): void { if (!text) - text = defaultText; + text = this.defaultText; if (text?.indexOf('\n') === -1) { this.eggGachaMessageBox.setSize(320, 32); @@ -490,7 +510,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { } showError(text: string): void { - this.showText(text, null, () => this.showText(defaultText), Utils.fixedInt(1500)); + this.showText(text, null, () => this.showText(this.defaultText), Utils.fixedInt(1500)); } setTransitioning(transitioning: boolean): void { @@ -526,27 +546,27 @@ export default class EggGachaUiHandler extends MessageUiHandler { case 0: if (!this.scene.gameData.voucherCounts[VoucherType.REGULAR]) { error = true; - this.showError('You don\'t have enough vouchers!'); + this.showError(i18next.t('egg:notEnoughVouchers')); } else if (this.scene.gameData.eggs.length < 99) { this.consumeVouchers(VoucherType.REGULAR, 1); this.pull(); success = true; } else { error = true; - this.showError('You have too many eggs!'); + this.showError(i18next.t('egg:tooManyEggs')); } break; case 2: if (!this.scene.gameData.voucherCounts[VoucherType.PLUS]) { error = true; - this.showError('You don\'t have enough vouchers!'); + this.showError(i18next.t('egg:notEnoughVouchers')); } else if (this.scene.gameData.eggs.length < 95) { this.consumeVouchers(VoucherType.PLUS, 1); this.pull(5); success = true; } else { error = true; - this.showError('You have too many eggs!'); + this.showError(i18next.t('egg:tooManyEggs')); } break; case 1: @@ -554,7 +574,7 @@ export default class EggGachaUiHandler extends MessageUiHandler { if ((this.cursor === 1 && this.scene.gameData.voucherCounts[VoucherType.REGULAR] < 10) || (this.cursor === 3 && !this.scene.gameData.voucherCounts[VoucherType.PREMIUM])) { error = true; - this.showError('You don\'t have enough vouchers!'); + this.showError(i18next.t('egg:notEnoughVouchers')); } else if (this.scene.gameData.eggs.length < 90) { if (this.cursor === 3) this.consumeVouchers(VoucherType.PREMIUM, 1); @@ -564,20 +584,20 @@ export default class EggGachaUiHandler extends MessageUiHandler { success = true; } else { error = true; - this.showError('You have too many eggs!'); + this.showError(i18next.t('egg:tooManyEggs')); } break; case 4: if (!this.scene.gameData.voucherCounts[VoucherType.GOLDEN]) { error = true; - this.showError('You don\'t have enough vouchers!'); + this.showError(i18next.t('egg:notEnoughVouchers')); } else if (this.scene.gameData.eggs.length < 75) { this.consumeVouchers(VoucherType.GOLDEN, 1); this.pull(25); success = true; } else { error = true; - this.showError('You have too many eggs!'); + this.showError(i18next.t('egg:tooManyEggs')); } break; case 5: diff --git a/src/ui/egg-list-ui-handler.ts b/src/ui/egg-list-ui-handler.ts index edeac7d71c7..a62eb743697 100644 --- a/src/ui/egg-list-ui-handler.ts +++ b/src/ui/egg-list-ui-handler.ts @@ -7,6 +7,7 @@ import { EGG_SEED, Egg, GachaType, getEggGachaTypeDescriptor, getEggHatchWavesMe import * as Utils from "../utils"; import { addWindow } from "./ui-theme"; import {Button} from "../enums/buttons"; +import i18next from '../plugins/i18n'; export default class EggListUiHandler extends MessageUiHandler { private eggListContainer: Phaser.GameObjects.Container; @@ -165,7 +166,7 @@ export default class EggListUiHandler extends MessageUiHandler { setEggDetails(egg: Egg): void { this.eggSprite.setFrame(`egg_${egg.getKey()}`); - this.eggNameText.setText(`Egg (${getEggDescriptor(egg)})`); + this.eggNameText.setText(`${i18next.t('egg:egg')} (${getEggDescriptor(egg)})`); this.eggDateText.setText( new Date(egg.timestamp).toLocaleString(undefined, { weekday: 'short', From 8dce9fa2f9f976ae206e8567e2cb997d08daf634 Mon Sep 17 00:00:00 2001 From: Alessandro Bruzzese <69127023+Bruzzii@users.noreply.github.com> Date: Thu, 16 May 2024 10:37:40 +0200 Subject: [PATCH 37/46] Added splash messages literals for all languages (#600) * Added splash messages literals for all languages * Removed debug code + fixed function casing --------- Co-authored-by: Benjamin Odom --- src/data/splash-messages.ts | 80 +++++++++++++++++-------------- src/locales/de/config.ts | 2 + src/locales/de/splash-messages.ts | 37 ++++++++++++++ src/locales/en/config.ts | 2 + src/locales/en/splash-messages.ts | 37 ++++++++++++++ src/locales/es/config.ts | 2 + src/locales/es/splash-messages.ts | 37 ++++++++++++++ src/locales/fr/config.ts | 2 + src/locales/fr/splash-messages.ts | 37 ++++++++++++++ src/locales/it/config.ts | 2 + src/locales/it/splash-messages.ts | 37 ++++++++++++++ src/plugins/i18n.ts | 1 + src/ui/title-ui-handler.ts | 8 ++-- 13 files changed, 244 insertions(+), 40 deletions(-) create mode 100644 src/locales/de/splash-messages.ts create mode 100644 src/locales/en/splash-messages.ts create mode 100644 src/locales/es/splash-messages.ts create mode 100644 src/locales/fr/splash-messages.ts create mode 100644 src/locales/it/splash-messages.ts diff --git a/src/data/splash-messages.ts b/src/data/splash-messages.ts index 198ff07cec9..3a40429e9b6 100644 --- a/src/data/splash-messages.ts +++ b/src/data/splash-messages.ts @@ -1,37 +1,45 @@ -export const battleCountSplashMessage = '{COUNT} Battles Won!'; +import i18next from "../plugins/i18n"; -export const splashMessages = Array(10).fill(battleCountSplashMessage); -splashMessages.push(...[ - 'Join the Discord!', - 'Infinite Levels!', - 'Everything Stacks!', - 'Optional Save Scumming!', - '35 Biomes!', - 'Open Source!', - 'Play with 5x Speed!', - 'Live Bug Testing!', - 'Heavy RoR2 Influence!', - 'Pokémon Risk and Pokémon Rain!', - 'Now with 33% More Salt!', - 'Infinite Fusion at Home!', - 'Broken Egg Moves!', - 'Magnificent!', - 'Mubstitute!', - 'That\'s Crazy!', - 'Orance Juice!', - 'Questionable Balancing!', - 'Cool Shaders!', - 'AI-Free!', - 'Sudden Difficulty Spikes!', - 'Based on an Unfinished Flash Game!', - 'More Addictive than Intended!', - 'Mostly Consistent Seeds!', - 'Achievement Points Don\'t Do Anything!', - 'You Do Not Start at Level 2000!', - 'Don\'t Talk About the Manaphy Egg Incident!', - 'Also Try Pokéngine!', - 'Also Try Emerald Rogue!', - 'Also Try Radical Red!', - 'Eevee Expo!', - 'YNOproject!' -]); \ No newline at end of file +export function getBattleCountSplashMessage(): string { + return `{COUNT} ${i18next.t('splashMessages:battlesWon')}`; +} + +export function getSplashMessages(): string[] { + const splashMessages = Array(10).fill(getBattleCountSplashMessage()); + splashMessages.push(...[ + i18next.t('splashMessages:joinTheDiscord'), + i18next.t('splashMessages:infiniteLevel'), + i18next.t('splashMessages:everythingStacks'), + i18next.t('splashMessages:optionalSaveScumming'), + i18next.t('splashMessages:biomes'), + i18next.t('splashMessages:openSource'), + i18next.t('splashMessages:playWith5xSpeed'), + i18next.t('splashMessages:liveBugTesting'), + i18next.t('splashMessages:heavyRoR2Influence'), + i18next.t('splashMessages:pokemonRiskAndPokemonRain'), + i18next.t('splashMessages:nowWithMoreSalt'), + i18next.t('splashMessages:infiniteFusionAtHome'), + i18next.t('splashMessages:brokenEggMoves'), + i18next.t('splashMessages:magnificent'), + i18next.t('splashMessages:mubstitute'), + i18next.t('splashMessages:thatsCrazy'), + i18next.t('splashMessages:oranceJuice'), + i18next.t('splashMessages:questionableBalancing'), + i18next.t('splashMessages:coolShaders'), + i18next.t('splashMessages:aiFree'), + i18next.t('splashMessages:suddenDifficultySpikes'), + i18next.t('splashMessages:basedOnAnUnfinishedFlashGame'), + i18next.t('splashMessages:moreAddictiveThanIntended'), + i18next.t('splashMessages:mostlyConsistentSeeds'), + i18next.t('splashMessages:achievementPointsDontDoAnything'), + i18next.t('splashMessages:youDoNotStartAtLevel'), + i18next.t('splashMessages:dontTalkAboutTheManaphyEggIncident'), + i18next.t('splashMessages:alsoTryPokengine'), + i18next.t('splashMessages:alsoTryEmeraldRogue'), + i18next.t('splashMessages:alsoTryRadicalRed'), + i18next.t('splashMessages:eeveeExpo'), + i18next.t('splashMessages:ynoproject'), + ]); + + return splashMessages +} \ No newline at end of file diff --git a/src/locales/de/config.ts b/src/locales/de/config.ts index 7c8b455ef3d..72200a5141c 100644 --- a/src/locales/de/config.ts +++ b/src/locales/de/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { splashMessages } from "./splash-messages" export const deConfig = { @@ -32,6 +33,7 @@ export const deConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, + splashMessages: splashMessages, nature: nature, growth: growth, modifierType: modifierType, diff --git a/src/locales/de/splash-messages.ts b/src/locales/de/splash-messages.ts new file mode 100644 index 00000000000..6815d7f1824 --- /dev/null +++ b/src/locales/de/splash-messages.ts @@ -0,0 +1,37 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const splashMessages: SimpleTranslationEntries = { + "battlesWon": "Battles Won!", + "joinTheDiscord": "Join the Discord!", + "infiniteLevels": "Infinite Levels!", + "everythingStacks": "Everything Stacks!", + "optionalSaveScumming": "Optional Save Scumming!", + "biomes": "35 Biomes!", + "openSource": "Open Source!", + "playWithSpeed": "Play with 5x Speed!", + "liveBugTesting": "Live Bug Testing!", + "heavyInfluence": "Heavy RoR2 Influence!", + "pokemonRiskAndPokemonRain": "Pokémon Risk and Pokémon Rain!", + "nowWithMoreSalt": "Now with 33% More Salt!", + "infiniteFusionAtHome": "Infinite Fusion at Home!", + "brokenEggMoves": "Broken Egg Moves!", + "magnificent": "Magnificent!", + "mubstitute": "Mubstitute!", + "thatsCrazy": "That\'s Crazy!", + "oranceJuice": "Orance Juice!", + "questionableBalancing": "Questionable Balancing!", + "coolShaders": "Cool Shaders!", + "aiFree": "AI-Free!", + "suddenDifficultySpikes": "Sudden Difficulty Spikes!", + "basedOnAnUnfinishedFlashGame": "Based on an Unfinished Flash Game!", + "moreAddictiveThanIntended": "More Addictive than Intended!", + "mostlyConsistentSeeds": "Mostly Consistent Seeds!", + "achievementPointsDontDoAnything": "Achievement Points Don\'t Do Anything!", + "youDoNotStartAtLevel": "You Do Not Start at Level 2000!", + "dontTalkAboutTheManaphyEggIncident": "Don\'t Talk About the Manaphy Egg Incident!", + "alsoTryPokengine": "Also Try Pokéngine!", + "alsoTryEmeraldRogue": "Also Try Emerald Rogue!", + "alsoTryRadicalRed": "Also Try Radical Red!", + "eeveeExpo": "Eevee Expo!", + "ynoproject": "YNOproject!", +} as const; \ No newline at end of file diff --git a/src/locales/en/config.ts b/src/locales/en/config.ts index f6b385fe433..295c3ff5c33 100644 --- a/src/locales/en/config.ts +++ b/src/locales/en/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,6 +34,7 @@ export const enConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, + splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, diff --git a/src/locales/en/splash-messages.ts b/src/locales/en/splash-messages.ts new file mode 100644 index 00000000000..6815d7f1824 --- /dev/null +++ b/src/locales/en/splash-messages.ts @@ -0,0 +1,37 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const splashMessages: SimpleTranslationEntries = { + "battlesWon": "Battles Won!", + "joinTheDiscord": "Join the Discord!", + "infiniteLevels": "Infinite Levels!", + "everythingStacks": "Everything Stacks!", + "optionalSaveScumming": "Optional Save Scumming!", + "biomes": "35 Biomes!", + "openSource": "Open Source!", + "playWithSpeed": "Play with 5x Speed!", + "liveBugTesting": "Live Bug Testing!", + "heavyInfluence": "Heavy RoR2 Influence!", + "pokemonRiskAndPokemonRain": "Pokémon Risk and Pokémon Rain!", + "nowWithMoreSalt": "Now with 33% More Salt!", + "infiniteFusionAtHome": "Infinite Fusion at Home!", + "brokenEggMoves": "Broken Egg Moves!", + "magnificent": "Magnificent!", + "mubstitute": "Mubstitute!", + "thatsCrazy": "That\'s Crazy!", + "oranceJuice": "Orance Juice!", + "questionableBalancing": "Questionable Balancing!", + "coolShaders": "Cool Shaders!", + "aiFree": "AI-Free!", + "suddenDifficultySpikes": "Sudden Difficulty Spikes!", + "basedOnAnUnfinishedFlashGame": "Based on an Unfinished Flash Game!", + "moreAddictiveThanIntended": "More Addictive than Intended!", + "mostlyConsistentSeeds": "Mostly Consistent Seeds!", + "achievementPointsDontDoAnything": "Achievement Points Don\'t Do Anything!", + "youDoNotStartAtLevel": "You Do Not Start at Level 2000!", + "dontTalkAboutTheManaphyEggIncident": "Don\'t Talk About the Manaphy Egg Incident!", + "alsoTryPokengine": "Also Try Pokéngine!", + "alsoTryEmeraldRogue": "Also Try Emerald Rogue!", + "alsoTryRadicalRed": "Also Try Radical Red!", + "eeveeExpo": "Eevee Expo!", + "ynoproject": "YNOproject!", +} as const; \ No newline at end of file diff --git a/src/locales/es/config.ts b/src/locales/es/config.ts index 84a05233616..6c36db3ed45 100644 --- a/src/locales/es/config.ts +++ b/src/locales/es/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,6 +34,7 @@ export const esConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, + splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, diff --git a/src/locales/es/splash-messages.ts b/src/locales/es/splash-messages.ts new file mode 100644 index 00000000000..6815d7f1824 --- /dev/null +++ b/src/locales/es/splash-messages.ts @@ -0,0 +1,37 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const splashMessages: SimpleTranslationEntries = { + "battlesWon": "Battles Won!", + "joinTheDiscord": "Join the Discord!", + "infiniteLevels": "Infinite Levels!", + "everythingStacks": "Everything Stacks!", + "optionalSaveScumming": "Optional Save Scumming!", + "biomes": "35 Biomes!", + "openSource": "Open Source!", + "playWithSpeed": "Play with 5x Speed!", + "liveBugTesting": "Live Bug Testing!", + "heavyInfluence": "Heavy RoR2 Influence!", + "pokemonRiskAndPokemonRain": "Pokémon Risk and Pokémon Rain!", + "nowWithMoreSalt": "Now with 33% More Salt!", + "infiniteFusionAtHome": "Infinite Fusion at Home!", + "brokenEggMoves": "Broken Egg Moves!", + "magnificent": "Magnificent!", + "mubstitute": "Mubstitute!", + "thatsCrazy": "That\'s Crazy!", + "oranceJuice": "Orance Juice!", + "questionableBalancing": "Questionable Balancing!", + "coolShaders": "Cool Shaders!", + "aiFree": "AI-Free!", + "suddenDifficultySpikes": "Sudden Difficulty Spikes!", + "basedOnAnUnfinishedFlashGame": "Based on an Unfinished Flash Game!", + "moreAddictiveThanIntended": "More Addictive than Intended!", + "mostlyConsistentSeeds": "Mostly Consistent Seeds!", + "achievementPointsDontDoAnything": "Achievement Points Don\'t Do Anything!", + "youDoNotStartAtLevel": "You Do Not Start at Level 2000!", + "dontTalkAboutTheManaphyEggIncident": "Don\'t Talk About the Manaphy Egg Incident!", + "alsoTryPokengine": "Also Try Pokéngine!", + "alsoTryEmeraldRogue": "Also Try Emerald Rogue!", + "alsoTryRadicalRed": "Also Try Radical Red!", + "eeveeExpo": "Eevee Expo!", + "ynoproject": "YNOproject!", +} as const; \ No newline at end of file diff --git a/src/locales/fr/config.ts b/src/locales/fr/config.ts index 84c20a957ed..f6245f4eeaa 100644 --- a/src/locales/fr/config.ts +++ b/src/locales/fr/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,6 +34,7 @@ export const frConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, + splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, diff --git a/src/locales/fr/splash-messages.ts b/src/locales/fr/splash-messages.ts new file mode 100644 index 00000000000..6815d7f1824 --- /dev/null +++ b/src/locales/fr/splash-messages.ts @@ -0,0 +1,37 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const splashMessages: SimpleTranslationEntries = { + "battlesWon": "Battles Won!", + "joinTheDiscord": "Join the Discord!", + "infiniteLevels": "Infinite Levels!", + "everythingStacks": "Everything Stacks!", + "optionalSaveScumming": "Optional Save Scumming!", + "biomes": "35 Biomes!", + "openSource": "Open Source!", + "playWithSpeed": "Play with 5x Speed!", + "liveBugTesting": "Live Bug Testing!", + "heavyInfluence": "Heavy RoR2 Influence!", + "pokemonRiskAndPokemonRain": "Pokémon Risk and Pokémon Rain!", + "nowWithMoreSalt": "Now with 33% More Salt!", + "infiniteFusionAtHome": "Infinite Fusion at Home!", + "brokenEggMoves": "Broken Egg Moves!", + "magnificent": "Magnificent!", + "mubstitute": "Mubstitute!", + "thatsCrazy": "That\'s Crazy!", + "oranceJuice": "Orance Juice!", + "questionableBalancing": "Questionable Balancing!", + "coolShaders": "Cool Shaders!", + "aiFree": "AI-Free!", + "suddenDifficultySpikes": "Sudden Difficulty Spikes!", + "basedOnAnUnfinishedFlashGame": "Based on an Unfinished Flash Game!", + "moreAddictiveThanIntended": "More Addictive than Intended!", + "mostlyConsistentSeeds": "Mostly Consistent Seeds!", + "achievementPointsDontDoAnything": "Achievement Points Don\'t Do Anything!", + "youDoNotStartAtLevel": "You Do Not Start at Level 2000!", + "dontTalkAboutTheManaphyEggIncident": "Don\'t Talk About the Manaphy Egg Incident!", + "alsoTryPokengine": "Also Try Pokéngine!", + "alsoTryEmeraldRogue": "Also Try Emerald Rogue!", + "alsoTryRadicalRed": "Also Try Radical Red!", + "eeveeExpo": "Eevee Expo!", + "ynoproject": "YNOproject!", +} as const; \ No newline at end of file diff --git a/src/locales/it/config.ts b/src/locales/it/config.ts index 0247a7e0f80..11b1b9e5628 100644 --- a/src/locales/it/config.ts +++ b/src/locales/it/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,6 +34,7 @@ export const itConfig = { pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, tutorial: tutorial, + splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, diff --git a/src/locales/it/splash-messages.ts b/src/locales/it/splash-messages.ts new file mode 100644 index 00000000000..3bddc68f0b5 --- /dev/null +++ b/src/locales/it/splash-messages.ts @@ -0,0 +1,37 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +export const splashMessages: SimpleTranslationEntries = { + "battlesWon": "Battaglie Vinte!", + "joinTheDiscord": "Entra nel Discord!", + "infiniteLevels": "Livelli Infiniti!", + "everythingStacks": "Tutto si impila!", + "optionalSaveScumming": "Salvataggio Facoltativo!", + "biomes": "35 Biomi!", + "openSource": "Open Source!", + "playWithSpeed": "Gioca con il 5x di Velocità!", + "liveBugTesting": "Test dei Bug in Tempo Reale!", + "heavyInfluence": "Influenzato da RoR2!", + "pokemonRiskAndPokemonRain": "Pokémon Risk e Pokémon Rain!", + "nowWithMoreSalt": "Adesso con il 33% di sale in più!", + "infiniteFusionAtHome": "Fusioni Infinite a Casa!", + "brokenEggMoves": "Mosse delle Uova Rotte!", + "magnificent": "Magnifico!", + "mubstitute": "Mubstitute!", + "thatsCrazy": "È Pazzesco!", + "oranceJuice": "Succo d\'Arancia!", + "questionableBalancing": "Bilanciamento Discutibile!", + "coolShaders": "Shader fantastici!", + "aiFree": "Senza Intelligenza Artificiale!", + "suddenDifficultySpikes": "Picchi di Difficoltà Improvvisi!", + "basedOnAnUnfinishedFlashGame": "Basato su un Gioco Flash Incompiuto!", + "moreAddictiveThanIntended": "Crea Dipendeza più del Dovuto!", + "mostlyConsistentSeeds": "Seeds Consistenti!", + "achievementPointsDontDoAnything": "I Punti Obiettivo non Fanno Nulla!", + "youDoNotStartAtLevel": "Non Cominci dal Livello 2000!", + "dontTalkAboutTheManaphyEggIncident": "Non Parlare dell'Incidente dell'Uovo di Manaphy!", + "alsoTryPokengine": "Prova anche Pokéngine!", + "alsoTryEmeraldRogue": "Prova anche Emerald Rogue!", + "alsoTryRadicalRed": "Prova anche Radical Red!", + "eeveeExpo": "Eevee Expo!", + "ynoproject": "YNOproject!", +} as const; \ No newline at end of file diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index ffd45317121..1e0363f1688 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -124,6 +124,7 @@ declare module 'i18next' { fightUiHandler: SimpleTranslationEntries; tutorial: SimpleTranslationEntries; starterSelectUiHandler: SimpleTranslationEntries; + splashMessages: SimpleTranslationEntries; nature: SimpleTranslationEntries; growth: SimpleTranslationEntries; egg: SimpleTranslationEntries; diff --git a/src/ui/title-ui-handler.ts b/src/ui/title-ui-handler.ts index c808611b093..4da4f189f6b 100644 --- a/src/ui/title-ui-handler.ts +++ b/src/ui/title-ui-handler.ts @@ -4,7 +4,7 @@ import OptionSelectUiHandler from "./option-select-ui-handler"; import { Mode } from "./ui"; import * as Utils from "../utils"; import { TextStyle, addTextObject } from "./text"; -import { battleCountSplashMessage, splashMessages } from "../data/splash-messages"; +import { getBattleCountSplashMessage, getSplashMessages } from "../data/splash-messages"; import i18next from "i18next"; export default class TitleUiHandler extends OptionSelectUiHandler { @@ -63,8 +63,8 @@ export default class TitleUiHandler extends OptionSelectUiHandler { .then(request => request.json()) .then(stats => { this.playerCountLabel.setText(`${stats.playerCount} ${i18next.t("menu:playersOnline")}`); - if (this.splashMessage === battleCountSplashMessage) - this.splashMessageText.setText(battleCountSplashMessage.replace('{COUNT}', stats.battleCount.toLocaleString('en-US'))); + if (this.splashMessage === getBattleCountSplashMessage()) + this.splashMessageText.setText(getBattleCountSplashMessage().replace('{COUNT}', stats.battleCount.toLocaleString('en-US'))); }) .catch(err => { console.error("Failed to fetch title stats:\n", err); @@ -75,7 +75,7 @@ export default class TitleUiHandler extends OptionSelectUiHandler { const ret = super.show(args); if (ret) { - this.splashMessage = Utils.randItem(splashMessages); + this.splashMessage = Utils.randItem(getSplashMessages()); this.splashMessageText.setText(this.splashMessage.replace('{COUNT}', '?')); const ui = this.getUi(); From 1254ca5c4c5ca212fe392c5b2808894fc920e50e Mon Sep 17 00:00:00 2001 From: 0xLondre$ <86735808+jdsajdas@users.noreply.github.com> Date: Thu, 16 May 2024 03:52:26 -0500 Subject: [PATCH 38/46] New spanish translations (#729) * New spanish translations * KO translation * hitResultSuperEffective IX gen --- src/locales/es/battle.ts | 10 +++++----- src/locales/es/fight-ui-handler.ts | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/locales/es/battle.ts b/src/locales/es/battle.ts index 76a73142ad6..5b4b696a9d2 100644 --- a/src/locales/es/battle.ts +++ b/src/locales/es/battle.ts @@ -14,11 +14,11 @@ export const battle: SimpleTranslationEntries = { "pokemonCaught": "¡{{pokemonName}} atrapado!", "pokemon": "Pokémon", "sendOutPokemon": "¡Adelante, {{pokemonName}}!", - "hitResultCriticalHit": "A critical hit!", - "hitResultSuperEffective": "It's super effective!", - "hitResultNotVeryEffective": "It's not very effective…", - "hitResultNoEffect": "It doesn't affect {{pokemonName}}!", - "hitResultOneHitKO": "It's a one-hit KO!", + "hitResultCriticalHit": "!Un golpe crítico!", + "hitResultSuperEffective": "!Es supereficaz!", + "hitResultNotVeryEffective": "No es muy eficaz…", + "hitResultNoEffect": "No afecta a {{pokemonName}}!", + "hitResultOneHitKO": "!KO en 1 golpe!", "attackFailed": "¡Pero ha fallado!", "attackHitsCount": `N.º de golpes: {{count}}.`, "expGain": "{{pokemonName}} ha ganado\n{{exp}} puntos de experiencia.", diff --git a/src/locales/es/fight-ui-handler.ts b/src/locales/es/fight-ui-handler.ts index 7a02ce66f3c..951d043d393 100644 --- a/src/locales/es/fight-ui-handler.ts +++ b/src/locales/es/fight-ui-handler.ts @@ -3,5 +3,5 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const fightUiHandler: SimpleTranslationEntries = { "pp": "PP", "power": "Potencia", - "accuracy": "Accuracy", + "accuracy": "Precisión", } as const; From b06190c4e73e4c7549ca6963d8851a78702b9653 Mon Sep 17 00:00:00 2001 From: Jannik Tappert <38758606+CodeTappert@users.noreply.github.com> Date: Thu, 16 May 2024 11:05:25 +0200 Subject: [PATCH 39/46] Issue #745 localized trainer names trainer classes and titles (#752) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Issue #745 - Added the option to localize titles, trainer names (for important trainers like elite 4, champs etc) and trainer classes. - Also i already did the whole localization for german (sorry thats the only language is speak other then english...) - Also renamed the trainer Type "student" to school_kid (because there apparently really is a trainer class called student since the gen 9 dlc) - And i changed it so it makes sure that i18 only gets initalized once (it may be needed to initalize it before the loading phase so the elite 4 titles etc can be localized) * Issue #745 - Removed stuff that wasnt meant for this branch * Translation of French trainers.ts * Translation of French trainers.ts * Translation of French trainers.ts * Fixed spelling on german translation * Fixed name of Hex Maniac * ADded missing "," that were lost in the merge * For Trainer Classes that have a female and male variant the correct name is now choosen. (If a language has both). Also added a safety net that if the female version does not exist it uses the one without the suffix * Reverting override.ts * Added ptBR trainers.ts (thanks to zé ricardo on discord) * Updates Pokefan to reflect the correct english spelling (in all languages that still have the english defaults) * Updated Rich_kid trainer typ to named correctly as "Rich Boy" in english and all non yet localized languages * Added that the title will get made lower case so the rival is correctly set * Reverted a formatting change that i didnt make intentionally --------- Co-authored-by: Lugiad --- src/data/biomes.ts | 4 +- src/data/dialogue.ts | 2 +- src/data/enums/trainer-type.ts | 2 +- src/data/trainer-config.ts | 971 +++++++++++++++++---------------- src/data/trainer-names.ts | 4 +- src/field/trainer.ts | 12 +- src/locales/de/config.ts | 6 +- src/locales/de/trainers.ts | 221 ++++++++ src/locales/en/config.ts | 6 +- src/locales/en/trainers.ts | 219 ++++++++ src/locales/es/config.ts | 6 +- src/locales/es/trainers.ts | 219 ++++++++ src/locales/fr/config.ts | 8 +- src/locales/fr/trainers.ts | 219 ++++++++ src/locales/it/config.ts | 6 +- src/locales/it/trainers.ts | 219 ++++++++ src/locales/pt_BR/trainers.ts | 219 ++++++++ src/locales/zh_CN/config.ts | 7 +- src/locales/zh_CN/trainers.ts | 218 ++++++++ src/plugins/i18n.ts | 17 +- 20 files changed, 2115 insertions(+), 470 deletions(-) create mode 100644 src/locales/de/trainers.ts create mode 100644 src/locales/en/trainers.ts create mode 100644 src/locales/es/trainers.ts create mode 100644 src/locales/fr/trainers.ts create mode 100644 src/locales/it/trainers.ts create mode 100644 src/locales/pt_BR/trainers.ts create mode 100644 src/locales/zh_CN/trainers.ts diff --git a/src/data/biomes.ts b/src/data/biomes.ts index db13158fab3..c4fb750542d 100644 --- a/src/data/biomes.ts +++ b/src/data/biomes.ts @@ -1647,7 +1647,7 @@ export const biomeTrainerPools: BiomeTrainerPools = { [BiomePoolTier.BOSS_ULTRA_RARE]: [] }, [Biome.GRASS]: { - [BiomePoolTier.COMMON]: [ TrainerType.BREEDER, TrainerType.STUDENT ], + [BiomePoolTier.COMMON]: [ TrainerType.BREEDER, TrainerType.SCHOOL_KID ], [BiomePoolTier.UNCOMMON]: [ TrainerType.ACE_TRAINER ], [BiomePoolTier.RARE]: [ TrainerType.BLACK_BELT ], [BiomePoolTier.SUPER_RARE]: [], @@ -7270,7 +7270,7 @@ export const biomeTrainerPools: BiomeTrainerPools = { ] ], [ TrainerType.STRIKER, [] ], - [ TrainerType.STUDENT, [ + [ TrainerType.SCHOOL_KID, [ [ Biome.GRASS, BiomePoolTier.COMMON ] ] ], diff --git a/src/data/dialogue.ts b/src/data/dialogue.ts index 830b5f43775..055e5627a52 100644 --- a/src/data/dialogue.ts +++ b/src/data/dialogue.ts @@ -288,7 +288,7 @@ export const trainerTypeDialogue = { ] } ], - [TrainerType.STUDENT]: [ + [TrainerType.SCHOOL_KID]: [ { encounter: [ `…Heehee. I'm confident in my calculations and analysis.`, diff --git a/src/data/enums/trainer-type.ts b/src/data/enums/trainer-type.ts index c30b098960c..c263baae3b7 100644 --- a/src/data/enums/trainer-type.ts +++ b/src/data/enums/trainer-type.ts @@ -43,7 +43,7 @@ export enum TrainerType { SMASHER, SNOW_WORKER, STRIKER, - STUDENT, + SCHOOL_KID, SWIMMER, TWINS, VETERAN, diff --git a/src/data/trainer-config.ts b/src/data/trainer-config.ts index 5284773e4b6..b797c918bd9 100644 --- a/src/data/trainer-config.ts +++ b/src/data/trainer-config.ts @@ -1,161 +1,163 @@ -import BattleScene, { startingWave } from "../battle-scene"; -import { ModifierTypeFunc, modifierTypes } from "../modifier/modifier-type"; -import { EnemyPokemon } from "../field/pokemon"; +import BattleScene, {startingWave} from "../battle-scene"; +import {ModifierTypeFunc, modifierTypes} from "../modifier/modifier-type"; +import {EnemyPokemon} from "../field/pokemon"; import * as Utils from "../utils"; -import { TrainerType } from "./enums/trainer-type"; -import { Moves } from "./enums/moves"; -import { PokeballType } from "./pokeball"; -import { pokemonEvolutions, pokemonPrevolutions } from "./pokemon-evolutions"; -import PokemonSpecies, { PokemonSpeciesFilter, getPokemonSpecies } from "./pokemon-species"; -import { Species } from "./enums/species"; -import { tmSpecies } from "./tms"; -import { Type } from "./type"; -import { initTrainerTypeDialogue } from "./dialogue"; -import { PersistentModifier } from "../modifier/modifier"; -import { TrainerVariant } from "../field/trainer"; -import { PartyMemberStrength } from "./enums/party-member-strength"; +import {TrainerType} from "./enums/trainer-type"; +import {Moves} from "./enums/moves"; +import {PokeballType} from "./pokeball"; +import {pokemonEvolutions, pokemonPrevolutions} from "./pokemon-evolutions"; +import PokemonSpecies, {PokemonSpeciesFilter, getPokemonSpecies} from "./pokemon-species"; +import {Species} from "./enums/species"; +import {tmSpecies} from "./tms"; +import {Type} from "./type"; +import {initTrainerTypeDialogue} from "./dialogue"; +import {PersistentModifier} from "../modifier/modifier"; +import {TrainerVariant} from "../field/trainer"; +import {PartyMemberStrength} from "./enums/party-member-strength"; +import i18next from "i18next"; +import {getIsInitialized, initI18n} from "#app/plugins/i18n"; export enum TrainerPoolTier { - COMMON, - UNCOMMON, - RARE, - SUPER_RARE, - ULTRA_RARE + COMMON, + UNCOMMON, + RARE, + SUPER_RARE, + ULTRA_RARE } export interface TrainerTierPools { - [key: integer]: Species[] + [key: integer]: Species[] } export enum TrainerSlot { - NONE, - TRAINER, - TRAINER_PARTNER + NONE, + TRAINER, + TRAINER_PARTNER } export class TrainerPartyTemplate { - public size: integer; - public strength: PartyMemberStrength; - public sameSpecies: boolean; - public balanced: boolean; + public size: integer; + public strength: PartyMemberStrength; + public sameSpecies: boolean; + public balanced: boolean; - constructor(size: integer, strength: PartyMemberStrength, sameSpecies?: boolean, balanced?: boolean) { - this.size = size; - this.strength = strength; - this.sameSpecies = !!sameSpecies; - this.balanced = !!balanced; - } + constructor(size: integer, strength: PartyMemberStrength, sameSpecies?: boolean, balanced?: boolean) { + this.size = size; + this.strength = strength; + this.sameSpecies = !!sameSpecies; + this.balanced = !!balanced; + } - getStrength(index: integer): PartyMemberStrength { - return this.strength; - } + getStrength(index: integer): PartyMemberStrength { + return this.strength; + } - isSameSpecies(index: integer): boolean { - return this.sameSpecies; - } + isSameSpecies(index: integer): boolean { + return this.sameSpecies; + } - isBalanced(index: integer): boolean { - return this.balanced; - } + isBalanced(index: integer): boolean { + return this.balanced; + } } export class TrainerPartyCompoundTemplate extends TrainerPartyTemplate { - public templates: TrainerPartyTemplate[]; + public templates: TrainerPartyTemplate[]; - constructor(...templates: TrainerPartyTemplate[]) { - super(templates.reduce((total: integer, template: TrainerPartyTemplate) => { - total += template.size; - return total; - }, 0), PartyMemberStrength.AVERAGE); - this.templates = templates; - } - - getStrength(index: integer): PartyMemberStrength { - let t = 0; - for (let template of this.templates) { - if (t + template.size > index) - return template.getStrength(index - t); - t += template.size; + constructor(...templates: TrainerPartyTemplate[]) { + super(templates.reduce((total: integer, template: TrainerPartyTemplate) => { + total += template.size; + return total; + }, 0), PartyMemberStrength.AVERAGE); + this.templates = templates; } - return super.getStrength(index); - } + getStrength(index: integer): PartyMemberStrength { + let t = 0; + for (let template of this.templates) { + if (t + template.size > index) + return template.getStrength(index - t); + t += template.size; + } - isSameSpecies(index: integer): boolean { - let t = 0; - for (let template of this.templates) { - if (t + template.size > index) - return template.isSameSpecies(index - t); - t += template.size; + return super.getStrength(index); } - return super.isSameSpecies(index); - } + isSameSpecies(index: integer): boolean { + let t = 0; + for (let template of this.templates) { + if (t + template.size > index) + return template.isSameSpecies(index - t); + t += template.size; + } - isBalanced(index: integer): boolean { - let t = 0; - for (let template of this.templates) { - if (t + template.size > index) - return template.isBalanced(index - t); - t += template.size; + return super.isSameSpecies(index); } - return super.isBalanced(index); - } + isBalanced(index: integer): boolean { + let t = 0; + for (let template of this.templates) { + if (t + template.size > index) + return template.isBalanced(index - t); + t += template.size; + } + + return super.isBalanced(index); + } } export const trainerPartyTemplates = { - ONE_WEAK_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - ONE_AVG: new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), - ONE_AVG_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - ONE_STRONG: new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), - ONE_STRONGER: new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER), - TWO_WEAKER: new TrainerPartyTemplate(2, PartyMemberStrength.WEAKER), - TWO_WEAK: new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), - TWO_WEAK_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), - TWO_WEAK_SAME_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), - TWO_WEAK_SAME_TWO_WEAK_SAME: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true), new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true)), - TWO_WEAK_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - TWO_AVG: new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), - TWO_AVG_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - TWO_AVG_SAME_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), - TWO_AVG_SAME_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - TWO_AVG_SAME_TWO_AVG_SAME: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true)), - TWO_STRONG: new TrainerPartyTemplate(2, PartyMemberStrength.STRONG), - THREE_WEAK: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK), - THREE_WEAK_SAME: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK, true), - THREE_AVG: new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), - THREE_AVG_SAME: new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, true), - THREE_WEAK_BALANCED: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK, false, true), - FOUR_WEAKER: new TrainerPartyTemplate(4, PartyMemberStrength.WEAKER), - FOUR_WEAKER_SAME: new TrainerPartyTemplate(4, PartyMemberStrength.WEAKER, true), - FOUR_WEAK: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK), - FOUR_WEAK_SAME: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK, true), - FOUR_WEAK_BALANCED: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK, false, true), - FIVE_WEAKER: new TrainerPartyTemplate(5, PartyMemberStrength.WEAKER), - FIVE_WEAK: new TrainerPartyTemplate(5, PartyMemberStrength.WEAK), - FIVE_WEAK_BALANCED: new TrainerPartyTemplate(5, PartyMemberStrength.WEAK, false, true), - SIX_WEAKER: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER), - SIX_WEAKER_SAME: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER, true), - SIX_WEAK_SAME: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER, true), - SIX_WEAK_BALANCED: new TrainerPartyTemplate(6, PartyMemberStrength.WEAK, false, true), + ONE_WEAK_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + ONE_AVG: new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), + ONE_AVG_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + ONE_STRONG: new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), + ONE_STRONGER: new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER), + TWO_WEAKER: new TrainerPartyTemplate(2, PartyMemberStrength.WEAKER), + TWO_WEAK: new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), + TWO_WEAK_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), + TWO_WEAK_SAME_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), + TWO_WEAK_SAME_TWO_WEAK_SAME: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true), new TrainerPartyTemplate(2, PartyMemberStrength.WEAK, true)), + TWO_WEAK_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.WEAK), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + TWO_AVG: new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), + TWO_AVG_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + TWO_AVG_SAME_ONE_AVG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), + TWO_AVG_SAME_ONE_STRONG: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + TWO_AVG_SAME_TWO_AVG_SAME: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true), new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, true)), + TWO_STRONG: new TrainerPartyTemplate(2, PartyMemberStrength.STRONG), + THREE_WEAK: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK), + THREE_WEAK_SAME: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK, true), + THREE_AVG: new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), + THREE_AVG_SAME: new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, true), + THREE_WEAK_BALANCED: new TrainerPartyTemplate(3, PartyMemberStrength.WEAK, false, true), + FOUR_WEAKER: new TrainerPartyTemplate(4, PartyMemberStrength.WEAKER), + FOUR_WEAKER_SAME: new TrainerPartyTemplate(4, PartyMemberStrength.WEAKER, true), + FOUR_WEAK: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK), + FOUR_WEAK_SAME: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK, true), + FOUR_WEAK_BALANCED: new TrainerPartyTemplate(4, PartyMemberStrength.WEAK, false, true), + FIVE_WEAKER: new TrainerPartyTemplate(5, PartyMemberStrength.WEAKER), + FIVE_WEAK: new TrainerPartyTemplate(5, PartyMemberStrength.WEAK), + FIVE_WEAK_BALANCED: new TrainerPartyTemplate(5, PartyMemberStrength.WEAK, false, true), + SIX_WEAKER: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER), + SIX_WEAKER_SAME: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER, true), + SIX_WEAK_SAME: new TrainerPartyTemplate(6, PartyMemberStrength.WEAKER, true), + SIX_WEAK_BALANCED: new TrainerPartyTemplate(6, PartyMemberStrength.WEAK, false, true), - GYM_LEADER_1: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - GYM_LEADER_2: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), - GYM_LEADER_3: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), - GYM_LEADER_4: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), - GYM_LEADER_5: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(2, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), + GYM_LEADER_1: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + GYM_LEADER_2: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), + GYM_LEADER_3: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), + GYM_LEADER_4: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), + GYM_LEADER_5: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(2, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), - ELITE_FOUR: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), + ELITE_FOUR: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)), - CHAMPION: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER), new TrainerPartyTemplate(5, PartyMemberStrength.STRONG, false, true)), + CHAMPION: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER), new TrainerPartyTemplate(5, PartyMemberStrength.STRONG, false, true)), - RIVAL: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), - RIVAL_2: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), - RIVAL_3: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), - RIVAL_4: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), - RIVAL_5: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), - RIVAL_6: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)) + RIVAL: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE)), + RIVAL_2: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), + RIVAL_3: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), + RIVAL_4: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(2, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.WEAK, false, true)), + RIVAL_5: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONG)), + RIVAL_6: new TrainerPartyCompoundTemplate(new TrainerPartyTemplate(1, PartyMemberStrength.STRONG), new TrainerPartyTemplate(1, PartyMemberStrength.AVERAGE), new TrainerPartyTemplate(3, PartyMemberStrength.AVERAGE, false, true), new TrainerPartyTemplate(1, PartyMemberStrength.STRONGER)) }; type PartyTemplateFunc = (scene: BattleScene) => TrainerPartyTemplate; @@ -163,368 +165,425 @@ type PartyMemberFunc = (scene: BattleScene, level: integer, strength: PartyMembe type GenModifiersFunc = (party: EnemyPokemon[]) => PersistentModifier[]; export interface PartyMemberFuncs { - [key: integer]: PartyMemberFunc + [key: integer]: PartyMemberFunc } export class TrainerConfig { - public trainerType: TrainerType; - public name: string; - public nameFemale: string; - public nameDouble: string; - public title: string; - public hasGenders: boolean = false; - public hasDouble: boolean = false; - public hasCharSprite: boolean = false; - public doubleOnly: boolean = false; - public moneyMultiplier: number = 1; - public isBoss: boolean = false; - public hasStaticParty: boolean = false; - public useSameSeedForAllMembers: boolean = false; - public battleBgm: string; - public encounterBgm: string; - public femaleEncounterBgm: string; - public doubleEncounterBgm: string; - public victoryBgm: string; - public genModifiersFunc: GenModifiersFunc; - public modifierRewardFuncs: ModifierTypeFunc[] = []; - public partyTemplates: TrainerPartyTemplate[]; - public partyTemplateFunc: PartyTemplateFunc; - public partyMemberFuncs: PartyMemberFuncs = {}; - public speciesPools: TrainerTierPools; - public speciesFilter: PokemonSpeciesFilter; - public specialtyTypes: Type[] = []; + public trainerType: TrainerType; + public name: string; + public nameFemale: string; + public nameDouble: string; + public title: string; + public hasGenders: boolean = false; + public hasDouble: boolean = false; + public hasCharSprite: boolean = false; + public doubleOnly: boolean = false; + public moneyMultiplier: number = 1; + public isBoss: boolean = false; + public hasStaticParty: boolean = false; + public useSameSeedForAllMembers: boolean = false; + public battleBgm: string; + public encounterBgm: string; + public femaleEncounterBgm: string; + public doubleEncounterBgm: string; + public victoryBgm: string; + public genModifiersFunc: GenModifiersFunc; + public modifierRewardFuncs: ModifierTypeFunc[] = []; + public partyTemplates: TrainerPartyTemplate[]; + public partyTemplateFunc: PartyTemplateFunc; + public partyMemberFuncs: PartyMemberFuncs = {}; + public speciesPools: TrainerTierPools; + public speciesFilter: PokemonSpeciesFilter; + public specialtyTypes: Type[] = []; - public encounterMessages: string[] = []; - public victoryMessages: string[] = []; - public defeatMessages: string[] = []; + public encounterMessages: string[] = []; + public victoryMessages: string[] = []; + public defeatMessages: string[] = []; - public femaleEncounterMessages: string[]; - public femaleVictoryMessages: string[]; - public femaleDefeatMessages: string[]; + public femaleEncounterMessages: string[]; + public femaleVictoryMessages: string[]; + public femaleDefeatMessages: string[]; - public doubleEncounterMessages: string[]; - public doubleVictoryMessages: string[]; - public doubleDefeatMessages: string[]; + public doubleEncounterMessages: string[]; + public doubleVictoryMessages: string[]; + public doubleDefeatMessages: string[]; - constructor(trainerType: TrainerType, allowLegendaries?: boolean) { - this.trainerType = trainerType; - this.name = Utils.toReadableString(TrainerType[this.getDerivedType()]); - this.battleBgm = 'battle_trainer'; - this.victoryBgm = 'victory_trainer'; - this.partyTemplates = [ trainerPartyTemplates.TWO_AVG ]; - this.speciesFilter = species => (allowLegendaries || (!species.legendary && !species.subLegendary && !species.mythical)) && !species.isTrainerForbidden(); - } - - getKey(): string { - return TrainerType[this.getDerivedType()].toString().toLowerCase(); - } - - getSpriteKey(female?: boolean): string { - let ret = this.getKey(); - if (this.hasGenders) - ret += `_${female ? 'f' : 'm'}`; - return ret; - } - - setName(name: string): TrainerConfig { - this.name = name; - return this; - } - - setTitle(title: string): TrainerConfig { - this.title = title; - return this; - } - - getDerivedType(): TrainerType { - let trainerType = this.trainerType; - switch (trainerType) { - case TrainerType.RIVAL_2: - case TrainerType.RIVAL_3: - case TrainerType.RIVAL_4: - case TrainerType.RIVAL_5: - case TrainerType.RIVAL_6: - trainerType = TrainerType.RIVAL; - break; - case TrainerType.LANCE_CHAMPION: - trainerType = TrainerType.LANCE; - break; - case TrainerType.LARRY_ELITE: - trainerType = TrainerType.LARRY; - break; + constructor(trainerType: TrainerType, allowLegendaries?: boolean) { + this.trainerType = trainerType; + this.name = Utils.toReadableString(TrainerType[this.getDerivedType()]); + this.battleBgm = 'battle_trainer'; + this.victoryBgm = 'victory_trainer'; + this.partyTemplates = [trainerPartyTemplates.TWO_AVG]; + this.speciesFilter = species => (allowLegendaries || (!species.legendary && !species.subLegendary && !species.mythical)) && !species.isTrainerForbidden(); } - return trainerType; - } - - setHasGenders(nameFemale?: string, femaleEncounterBgm?: TrainerType | string): TrainerConfig { - this.hasGenders = true; - this.nameFemale = nameFemale; - if (femaleEncounterBgm) - this.femaleEncounterBgm = typeof femaleEncounterBgm === 'number' ? TrainerType[femaleEncounterBgm].toString().replace(/\_/g, ' ').toLowerCase() : femaleEncounterBgm; - return this; - } - - setHasDouble(nameDouble: string, doubleEncounterBgm?: TrainerType | string): TrainerConfig { - this.hasDouble = true; - this.nameDouble = nameDouble; - if (doubleEncounterBgm) - this.doubleEncounterBgm = typeof doubleEncounterBgm === 'number' ? TrainerType[doubleEncounterBgm].toString().replace(/\_/g, ' ').toLowerCase() : doubleEncounterBgm; - return this; - } - - setHasCharSprite(): TrainerConfig { - this.hasCharSprite = true; - return this; - } - - setDoubleOnly(): TrainerConfig { - this.doubleOnly = true; - return this; - } - - setMoneyMultiplier(moneyMultiplier: number): TrainerConfig { - this.moneyMultiplier = moneyMultiplier; - return this; - } - - setBoss(): TrainerConfig { - this.isBoss = true; - return this; - } - - setStaticParty(): TrainerConfig { - this.hasStaticParty = true; - return this; - } - - setUseSameSeedForAllMembers(): TrainerConfig { - this.useSameSeedForAllMembers = true; - return this; - } - - setBattleBgm(battleBgm: string): TrainerConfig { - this.battleBgm = battleBgm; - return this; - } - - setEncounterBgm(encounterBgm: TrainerType | string): TrainerConfig { - this.encounterBgm = typeof encounterBgm === 'number' ? TrainerType[encounterBgm].toString().toLowerCase() : encounterBgm; - return this; - } - - setVictoryBgm(victoryBgm: string): TrainerConfig { - this.victoryBgm = victoryBgm; - return this; - } - - setPartyTemplates(...partyTemplates: TrainerPartyTemplate[]): TrainerConfig { - this.partyTemplates = partyTemplates; - return this; - } - - setPartyTemplateFunc(partyTemplateFunc: PartyTemplateFunc): TrainerConfig { - this.partyTemplateFunc = partyTemplateFunc; - return this; - } - - setPartyMemberFunc(slotIndex: integer, partyMemberFunc: PartyMemberFunc): TrainerConfig { - this.partyMemberFuncs[slotIndex] = partyMemberFunc; - return this; - } - - setSpeciesPools(speciesPools: TrainerTierPools | Species[]): TrainerConfig { - this.speciesPools = (Array.isArray(speciesPools) ? { [TrainerPoolTier.COMMON]: speciesPools } : speciesPools) as unknown as TrainerTierPools; - return this; - } - - setSpeciesFilter(speciesFilter: PokemonSpeciesFilter, allowLegendaries?: boolean): TrainerConfig { - const baseFilter = this.speciesFilter; - this.speciesFilter = allowLegendaries ? speciesFilter : species => speciesFilter(species) && baseFilter(species); - return this; - } - - setSpecialtyTypes(...specialtyTypes: Type[]): TrainerConfig { - this.specialtyTypes = specialtyTypes; - return this; - } - - setGenModifiersFunc(genModifiersFunc: GenModifiersFunc): TrainerConfig { - this.genModifiersFunc = genModifiersFunc; - return this; - } - - setModifierRewardFuncs(...modifierTypeFuncs: (() => ModifierTypeFunc)[]): TrainerConfig { - this.modifierRewardFuncs = modifierTypeFuncs.map(func => () => { - const modifierTypeFunc = func(); - const modifierType = modifierTypeFunc(); - modifierType.withIdFromFunc(modifierTypeFunc); - return modifierType; - }); - return this; - } - - initForGymLeader(signatureSpecies: (Species | Species[])[], ...specialtyTypes: Type[]): TrainerConfig { - this.setPartyTemplateFunc(getGymLeaderPartyTemplate); - signatureSpecies.forEach((speciesPool, s) => { - if (!Array.isArray(speciesPool)) - speciesPool = [ speciesPool ]; - this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); - }); - if (specialtyTypes.length) { - this.setSpeciesFilter(p => specialtyTypes.find(t => p.isOfType(t)) !== undefined); - this.setSpecialtyTypes(...specialtyTypes); - } - this.setTitle('Gym Leader'); - this.setMoneyMultiplier(2.5); - this.setBoss(); - this.setStaticParty(); - this.setBattleBgm('battle_unova_gym'); - this.setVictoryBgm('victory_gym'); - this.setGenModifiersFunc(party => { - const waveIndex = party[0].scene.currentBattle.waveIndex; - return getRandomTeraModifiers(party, waveIndex >= 100 ? 1 : 0, specialtyTypes.length ? specialtyTypes : null); - }); - return this; - } - - initForEliteFour(signatureSpecies: (Species | Species[])[], ...specialtyTypes: Type[]): TrainerConfig { - this.setPartyTemplates(trainerPartyTemplates.ELITE_FOUR); - signatureSpecies.forEach((speciesPool, s) => { - if (!Array.isArray(speciesPool)) - speciesPool = [ speciesPool ]; - this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); - }); - if (specialtyTypes.length) { - this.setSpeciesFilter(p => specialtyTypes.find(t => p.isOfType(t)) && p.baseTotal >= 450); - this.setSpecialtyTypes(...specialtyTypes); - } else - this.setSpeciesFilter(p => p.baseTotal >= 450); - this.setTitle('Elite Four'); - this.setMoneyMultiplier(3.25); - this.setBoss(); - this.setStaticParty(); - this.setBattleBgm('battle_elite'); - this.setVictoryBgm('victory_gym'); - this.setGenModifiersFunc(party => getRandomTeraModifiers(party, 2, specialtyTypes.length ? specialtyTypes : null)); - return this; - } - - initForChampion(signatureSpecies: (Species | Species[])[]): TrainerConfig { - this.setPartyTemplates(trainerPartyTemplates.CHAMPION); - signatureSpecies.forEach((speciesPool, s) => { - if (!Array.isArray(speciesPool)) - speciesPool = [ speciesPool ]; - this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); - }); - this.setSpeciesFilter(p => p.baseTotal >= 470); - this.setTitle('Champion'); - this.setMoneyMultiplier(10); - this.setBoss(); - this.setStaticParty(); - this.setBattleBgm('battle_champion_alder'); - this.setVictoryBgm('victory_champion'); - this.setGenModifiersFunc(party => getRandomTeraModifiers(party, 3)); - return this; - } - - getTitle(trainerSlot: TrainerSlot = TrainerSlot.NONE, variant: TrainerVariant): string { - let ret = this.name; - - if (!trainerSlot && variant === TrainerVariant.DOUBLE && this.nameDouble) - return this.nameDouble; - - if (this.hasGenders) { - if (this.nameFemale) { - if (variant === TrainerVariant.FEMALE || (variant === TrainerVariant.DOUBLE && trainerSlot === TrainerSlot.TRAINER_PARTNER)) - return this.nameFemale; - } else - ret += !variant ? '♂' : '♀'; + getKey(): string { + return TrainerType[this.getDerivedType()].toString().toLowerCase(); } - return ret; - } + getSpriteKey(female?: boolean): string { + let ret = this.getKey(); + if (this.hasGenders) + ret += `_${female ? 'f' : 'm'}`; + return ret; + } + + setName(name: string): TrainerConfig { + if (name === 'Finn' || name === 'Ivy') { + // Give the rival a localized name + // First check if i18n is initialized + if (!getIsInitialized()) { + initI18n(); + } + if (name === 'Finn') { + this.name = i18next.t('trainerNames:rival'); + } + if (name === 'Ivy') { + this.name = i18next.t('trainerNames:rival_female'); + } - loadAssets(scene: BattleScene, variant: TrainerVariant): Promise { - return new Promise(resolve => { - const isDouble = variant === TrainerVariant.DOUBLE; - const trainerKey = this.getSpriteKey(variant === TrainerVariant.FEMALE); - const partnerTrainerKey = this.getSpriteKey(true); - scene.loadAtlas(trainerKey, 'trainer'); - if (isDouble) - scene.loadAtlas(partnerTrainerKey, 'trainer'); - scene.load.once(Phaser.Loader.Events.COMPLETE, () => { - const originalWarn = console.warn; - // Ignore warnings for missing frames, because there will be a lot - console.warn = () => {}; - const frameNames = scene.anims.generateFrameNames(trainerKey, { zeroPad: 4, suffix: ".png", start: 1, end: 128 }); - const partnerFrameNames = isDouble - ? scene.anims.generateFrameNames(partnerTrainerKey, { zeroPad: 4, suffix: ".png", start: 1, end: 128 }) - : null; - console.warn = originalWarn; - scene.anims.create({ - key: trainerKey, - frames: frameNames, - frameRate: 24, - repeat: -1 - }); - if (isDouble) { - scene.anims.create({ - key: partnerTrainerKey, - frames: partnerFrameNames, - frameRate: 24, - repeat: -1 - }); } - resolve(); - }); - if (!scene.load.isLoading()) - scene.load.start(); - }); - } + this.name = name; + return this; + } + + setTitle(title: string): TrainerConfig { + // First check if i18n is initialized + if (!getIsInitialized()) { + initI18n(); + } + + // Make the title lowercase and replace spaces with underscores + title = title.toLowerCase().replace(/\s/g, '_'); + + this.title = i18next.t(`titles:${title}`); + + + return this; + } + + getDerivedType(): TrainerType { + let trainerType = this.trainerType; + switch (trainerType) { + case TrainerType.RIVAL_2: + case TrainerType.RIVAL_3: + case TrainerType.RIVAL_4: + case TrainerType.RIVAL_5: + case TrainerType.RIVAL_6: + trainerType = TrainerType.RIVAL; + break; + case TrainerType.LANCE_CHAMPION: + trainerType = TrainerType.LANCE; + break; + case TrainerType.LARRY_ELITE: + trainerType = TrainerType.LARRY; + break; + } + + return trainerType; + } + + setHasGenders(nameFemale?: string, femaleEncounterBgm?: TrainerType | string): TrainerConfig { + this.hasGenders = true; + this.nameFemale = nameFemale; + if (femaleEncounterBgm) + this.femaleEncounterBgm = typeof femaleEncounterBgm === 'number' ? TrainerType[femaleEncounterBgm].toString().replace(/\_/g, ' ').toLowerCase() : femaleEncounterBgm; + return this; + } + + setHasDouble(nameDouble: string, doubleEncounterBgm?: TrainerType | string): TrainerConfig { + this.hasDouble = true; + this.nameDouble = nameDouble; + if (doubleEncounterBgm) + this.doubleEncounterBgm = typeof doubleEncounterBgm === 'number' ? TrainerType[doubleEncounterBgm].toString().replace(/\_/g, ' ').toLowerCase() : doubleEncounterBgm; + return this; + } + + setHasCharSprite(): TrainerConfig { + this.hasCharSprite = true; + return this; + } + + setDoubleOnly(): TrainerConfig { + this.doubleOnly = true; + return this; + } + + setMoneyMultiplier(moneyMultiplier: number): TrainerConfig { + this.moneyMultiplier = moneyMultiplier; + return this; + } + + setBoss(): TrainerConfig { + this.isBoss = true; + return this; + } + + setStaticParty(): TrainerConfig { + this.hasStaticParty = true; + return this; + } + + setUseSameSeedForAllMembers(): TrainerConfig { + this.useSameSeedForAllMembers = true; + return this; + } + + setBattleBgm(battleBgm: string): TrainerConfig { + this.battleBgm = battleBgm; + return this; + } + + setEncounterBgm(encounterBgm: TrainerType | string): TrainerConfig { + this.encounterBgm = typeof encounterBgm === 'number' ? TrainerType[encounterBgm].toString().toLowerCase() : encounterBgm; + return this; + } + + setVictoryBgm(victoryBgm: string): TrainerConfig { + this.victoryBgm = victoryBgm; + return this; + } + + setPartyTemplates(...partyTemplates: TrainerPartyTemplate[]): TrainerConfig { + this.partyTemplates = partyTemplates; + return this; + } + + setPartyTemplateFunc(partyTemplateFunc: PartyTemplateFunc): TrainerConfig { + this.partyTemplateFunc = partyTemplateFunc; + return this; + } + + setPartyMemberFunc(slotIndex: integer, partyMemberFunc: PartyMemberFunc): TrainerConfig { + this.partyMemberFuncs[slotIndex] = partyMemberFunc; + return this; + } + + setSpeciesPools(speciesPools: TrainerTierPools | Species[]): TrainerConfig { + this.speciesPools = (Array.isArray(speciesPools) ? {[TrainerPoolTier.COMMON]: speciesPools} : speciesPools) as unknown as TrainerTierPools; + return this; + } + + setSpeciesFilter(speciesFilter: PokemonSpeciesFilter, allowLegendaries?: boolean): TrainerConfig { + const baseFilter = this.speciesFilter; + this.speciesFilter = allowLegendaries ? speciesFilter : species => speciesFilter(species) && baseFilter(species); + return this; + } + + setSpecialtyTypes(...specialtyTypes: Type[]): TrainerConfig { + this.specialtyTypes = specialtyTypes; + return this; + } + + setGenModifiersFunc(genModifiersFunc: GenModifiersFunc): TrainerConfig { + this.genModifiersFunc = genModifiersFunc; + return this; + } + + setModifierRewardFuncs(...modifierTypeFuncs: (() => ModifierTypeFunc)[]): TrainerConfig { + this.modifierRewardFuncs = modifierTypeFuncs.map(func => () => { + const modifierTypeFunc = func(); + const modifierType = modifierTypeFunc(); + modifierType.withIdFromFunc(modifierTypeFunc); + return modifierType; + }); + return this; + } + + initForGymLeader(signatureSpecies: (Species | Species[])[], ...specialtyTypes: Type[]): TrainerConfig { + + this.setPartyTemplateFunc(getGymLeaderPartyTemplate); + signatureSpecies.forEach((speciesPool, s) => { + if (!Array.isArray(speciesPool)) + speciesPool = [speciesPool]; + this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); + }); + if (specialtyTypes.length) { + this.setSpeciesFilter(p => specialtyTypes.find(t => p.isOfType(t)) !== undefined); + this.setSpecialtyTypes(...specialtyTypes); + } + + // Handle name by checking this.name - making it lowercase and replacing spaces with underscores and then calling i18next.t with the name + const nameForCall = this.name.toLowerCase().replace(/\s/g, '_'); + this.name = i18next.t(`trainerNames:${nameForCall}`); + + + + this.setTitle("gym_leader"); + this.setMoneyMultiplier(2.5); + this.setBoss(); + this.setStaticParty(); + this.setBattleBgm('battle_unova_gym'); + this.setVictoryBgm('victory_gym'); + this.setGenModifiersFunc(party => { + const waveIndex = party[0].scene.currentBattle.waveIndex; + return getRandomTeraModifiers(party, waveIndex >= 100 ? 1 : 0, specialtyTypes.length ? specialtyTypes : null); + }); + return this; + } + + initForEliteFour(signatureSpecies: (Species | Species[])[], ...specialtyTypes: Type[]): TrainerConfig { + + + this.setPartyTemplates(trainerPartyTemplates.ELITE_FOUR); + signatureSpecies.forEach((speciesPool, s) => { + if (!Array.isArray(speciesPool)) + speciesPool = [speciesPool]; + this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); + }); + if (specialtyTypes.length) { + this.setSpeciesFilter(p => specialtyTypes.find(t => p.isOfType(t)) && p.baseTotal >= 450); + this.setSpecialtyTypes(...specialtyTypes); + } else + this.setSpeciesFilter(p => p.baseTotal >= 450); + // Handle name by checking this.name - making it lowercase and replacing spaces with underscores and then calling i18next.t with the name + const nameForCall = this.name.toLowerCase().replace(/\s/g, '_'); + this.name = i18next.t(`trainerNames:${nameForCall}`); + + this.setTitle("elite_four"); + this.setMoneyMultiplier(3.25); + this.setBoss(); + this.setStaticParty(); + this.setBattleBgm('battle_elite'); + this.setVictoryBgm('victory_gym'); + this.setGenModifiersFunc(party => getRandomTeraModifiers(party, 2, specialtyTypes.length ? specialtyTypes : null)); + return this; + } + + initForChampion(signatureSpecies: (Species | Species[])[]): TrainerConfig { + + this.setPartyTemplates(trainerPartyTemplates.CHAMPION); + signatureSpecies.forEach((speciesPool, s) => { + if (!Array.isArray(speciesPool)) + speciesPool = [speciesPool]; + this.setPartyMemberFunc(-(s + 1), getRandomPartyMemberFunc(speciesPool)); + }); + this.setSpeciesFilter(p => p.baseTotal >= 470); + // Handle name by checking this.name - making it lowercase and replacing spaces with underscores and then calling i18next.t with the name + const nameForCall = this.name.toLowerCase().replace(/\s/g, '_'); + this.name = i18next.t(`trainerNames:${nameForCall}`); + this.setTitle("champion"); + this.setMoneyMultiplier(10); + this.setBoss(); + this.setStaticParty(); + this.setBattleBgm('battle_champion_alder'); + this.setVictoryBgm('victory_champion'); + this.setGenModifiersFunc(party => getRandomTeraModifiers(party, 3)); + return this; + } + + getTitle(trainerSlot: TrainerSlot = TrainerSlot.NONE, variant: TrainerVariant): string { + let ret = this.name; + + if (!trainerSlot && variant === TrainerVariant.DOUBLE && this.nameDouble) + return this.nameDouble; + + if (this.hasGenders) { + if (this.nameFemale) { + if (variant === TrainerVariant.FEMALE || (variant === TrainerVariant.DOUBLE && trainerSlot === TrainerSlot.TRAINER_PARTNER)) + return this.nameFemale; + } else + + // Check if !variant is true, if so return the name, else return the name with _female appended + if (variant) { + if (!getIsInitialized()) { + initI18n(); + } + // Check if the female version exists in the i18n file + if (i18next.exists(`trainerClasses:${this.name.toLowerCase().replace}`)) { + // If it does, return + return ret + "_female"; + } else { + // If it doesn't, we do not do anything and go to the normal return + // This is to prevent the game from displaying an error if a female version of the trainer does not exist in the localization + } + } + } + + return ret; + } + + loadAssets(scene: BattleScene, variant: TrainerVariant): Promise { + return new Promise(resolve => { + const isDouble = variant === TrainerVariant.DOUBLE; + const trainerKey = this.getSpriteKey(variant === TrainerVariant.FEMALE); + const partnerTrainerKey = this.getSpriteKey(true); + scene.loadAtlas(trainerKey, 'trainer'); + if (isDouble) + scene.loadAtlas(partnerTrainerKey, 'trainer'); + scene.load.once(Phaser.Loader.Events.COMPLETE, () => { + const originalWarn = console.warn; + // Ignore warnings for missing frames, because there will be a lot + console.warn = () => { + }; + const frameNames = scene.anims.generateFrameNames(trainerKey, {zeroPad: 4,suffix: ".png",start: 1,end: 128}); + const partnerFrameNames = isDouble + ? scene.anims.generateFrameNames(partnerTrainerKey, {zeroPad: 4,suffix: ".png",start: 1,end: 128}) + : null; + console.warn = originalWarn; + scene.anims.create({ + key: trainerKey, + frames: frameNames, + frameRate: 24, + repeat: -1 + }); + if (isDouble) { + scene.anims.create({ + key: partnerTrainerKey, + frames: partnerFrameNames, + frameRate: 24, + repeat: -1 + }); + } + resolve(); + }); + if (!scene.load.isLoading()) + scene.load.start(); + }); + } } let t = 0; interface TrainerConfigs { - [key: integer]: TrainerConfig + [key: integer]: TrainerConfig } function getWavePartyTemplate(scene: BattleScene, ...templates: TrainerPartyTemplate[]) { - return templates[Math.min(Math.max(Math.ceil((scene.gameMode.getWaveForDifficulty(scene.currentBattle?.waveIndex || startingWave, true) - 20) / 30), 0), templates.length - 1)]; + return templates[Math.min(Math.max(Math.ceil((scene.gameMode.getWaveForDifficulty(scene.currentBattle?.waveIndex || startingWave, true) - 20) / 30), 0), templates.length - 1)]; } function getGymLeaderPartyTemplate(scene: BattleScene) { - return getWavePartyTemplate(scene, trainerPartyTemplates.GYM_LEADER_1, trainerPartyTemplates.GYM_LEADER_2, trainerPartyTemplates.GYM_LEADER_3, trainerPartyTemplates.GYM_LEADER_4, trainerPartyTemplates.GYM_LEADER_5); + return getWavePartyTemplate(scene, trainerPartyTemplates.GYM_LEADER_1, trainerPartyTemplates.GYM_LEADER_2, trainerPartyTemplates.GYM_LEADER_3, trainerPartyTemplates.GYM_LEADER_4, trainerPartyTemplates.GYM_LEADER_5); } function getRandomPartyMemberFunc(speciesPool: Species[], trainerSlot: TrainerSlot = TrainerSlot.TRAINER, ignoreEvolution: boolean = false, postProcess?: (enemyPokemon: EnemyPokemon) => void): PartyMemberFunc { - return (scene: BattleScene, level: integer, strength: PartyMemberStrength) => { - let species = Utils.randSeedItem(speciesPool); - if (!ignoreEvolution) - species = getPokemonSpecies(species).getTrainerSpeciesForLevel(level, true, strength); - return scene.addEnemyPokemon(getPokemonSpecies(species), level, trainerSlot, undefined, undefined, postProcess); - }; + return (scene: BattleScene, level: integer, strength: PartyMemberStrength) => { + let species = Utils.randSeedItem(speciesPool); + if (!ignoreEvolution) + species = getPokemonSpecies(species).getTrainerSpeciesForLevel(level, true, strength); + return scene.addEnemyPokemon(getPokemonSpecies(species), level, trainerSlot, undefined, undefined, postProcess); + }; } function getSpeciesFilterRandomPartyMemberFunc(speciesFilter: PokemonSpeciesFilter, trainerSlot: TrainerSlot = TrainerSlot.TRAINER, allowLegendaries?: boolean, postProcess?: (EnemyPokemon: EnemyPokemon) => void): PartyMemberFunc { - const originalSpeciesFilter = speciesFilter; - speciesFilter = (species: PokemonSpecies) => (allowLegendaries || (!species.legendary && !species.subLegendary && !species.mythical)) && !species.isTrainerForbidden() && originalSpeciesFilter(species); - return (scene: BattleScene, level: integer, strength: PartyMemberStrength) => { - const ret = scene.addEnemyPokemon(getPokemonSpecies(scene.randomSpecies(scene.currentBattle.waveIndex, level, false, speciesFilter).getTrainerSpeciesForLevel(level, true, strength)), level, trainerSlot, undefined, undefined, postProcess); - return ret; - }; + const originalSpeciesFilter = speciesFilter; + speciesFilter = (species: PokemonSpecies) => (allowLegendaries || (!species.legendary && !species.subLegendary && !species.mythical)) && !species.isTrainerForbidden() && originalSpeciesFilter(species); + return (scene: BattleScene, level: integer, strength: PartyMemberStrength) => { + const ret = scene.addEnemyPokemon(getPokemonSpecies(scene.randomSpecies(scene.currentBattle.waveIndex, level, false, speciesFilter).getTrainerSpeciesForLevel(level, true, strength)), level, trainerSlot, undefined, undefined, postProcess); + return ret; + }; } function getRandomTeraModifiers(party: EnemyPokemon[], count: integer, types?: Type[]): PersistentModifier[] { - const ret: PersistentModifier[] = []; - const partyMemberIndexes = new Array(party.length).fill(null).map((_, i) => i); - for (let t = 0; t < Math.min(count, party.length); t++) { - const randomIndex = Utils.randSeedItem(partyMemberIndexes); - partyMemberIndexes.splice(partyMemberIndexes.indexOf(randomIndex), 1); - ret.push(modifierTypes.TERA_SHARD().generateType(null, [ Utils.randSeedItem(types ? types : party[randomIndex].getTypes()) ]).withIdFromFunc(modifierTypes.TERA_SHARD).newModifier(party[randomIndex]) as PersistentModifier); - } - return ret; + const ret: PersistentModifier[] = []; + const partyMemberIndexes = new Array(party.length).fill(null).map((_, i) => i); + for (let t = 0; t < Math.min(count, party.length); t++) { + const randomIndex = Utils.randSeedItem(partyMemberIndexes); + partyMemberIndexes.splice(partyMemberIndexes.indexOf(randomIndex), 1); + ret.push(modifierTypes.TERA_SHARD().generateType(null, [Utils.randSeedItem(types ? types : party[randomIndex].getTypes())]).withIdFromFunc(modifierTypes.TERA_SHARD).newModifier(party[randomIndex]) as PersistentModifier); + } + return ret; } export const trainerConfigs: TrainerConfigs = { @@ -662,7 +721,7 @@ export const trainerConfigs: TrainerConfigs = { [TrainerType.SMASHER]: new TrainerConfig(++t).setMoneyMultiplier(1.2).setEncounterBgm(TrainerType.CYCLIST), [TrainerType.SNOW_WORKER]: new TrainerConfig(++t).setName('Worker').setHasGenders().setHasDouble('Workers').setMoneyMultiplier(1.7).setEncounterBgm(TrainerType.CLERK).setSpeciesFilter(s => s.isOfType(Type.ICE) || s.isOfType(Type.STEEL)), [TrainerType.STRIKER]: new TrainerConfig(++t).setMoneyMultiplier(1.2).setEncounterBgm(TrainerType.CYCLIST), - [TrainerType.STUDENT]: new TrainerConfig(++t).setMoneyMultiplier(0.75).setEncounterBgm(TrainerType.YOUNGSTER).setHasGenders(undefined, 'lass').setHasDouble('Students') + [TrainerType.SCHOOL_KID]: new TrainerConfig(++t).setMoneyMultiplier(0.75).setEncounterBgm(TrainerType.YOUNGSTER).setHasGenders(undefined, 'lass').setHasDouble('Students') .setSpeciesPools({ [TrainerPoolTier.COMMON]: [ Species.ODDISH, Species.EXEGGCUTE, Species.TEDDIURSA, Species.WURMPLE, Species.RALTS, Species.SHROOMISH, Species.FLETCHLING ], [TrainerPoolTier.UNCOMMON]: [ Species.VOLTORB, Species.WHISMUR, Species.MEDITITE, Species.MIME_JR, Species.NYMBLE ], @@ -880,6 +939,6 @@ export const trainerConfigs: TrainerConfigs = { }), }; -(function() { - initTrainerTypeDialogue(); -})(); \ No newline at end of file +(function () { + initTrainerTypeDialogue(); +})(); diff --git a/src/data/trainer-names.ts b/src/data/trainer-names.ts index 348976eae92..2b95a91314e 100644 --- a/src/data/trainer-names.ts +++ b/src/data/trainer-names.ts @@ -61,7 +61,7 @@ const trainerNameConfigs: TrainerNameConfigs = { [TrainerType.SMASHER]: new TrainerNameConfig(TrainerType.SMASHER), [TrainerType.SNOW_WORKER]: new TrainerNameConfig(TrainerType.SNOW_WORKER, 'Worker'), [TrainerType.STRIKER]: new TrainerNameConfig(TrainerType.STRIKER), - [TrainerType.STUDENT]: new TrainerNameConfig(TrainerType.STUDENT, 'School_Kid'), + [TrainerType.SCHOOL_KID]: new TrainerNameConfig(TrainerType.SCHOOL_KID, 'School_Kid'), [TrainerType.SWIMMER]: new TrainerNameConfig(TrainerType.SWIMMER), [TrainerType.TWINS]: new TrainerNameConfig(TrainerType.TWINS), [TrainerType.VETERAN]: new TrainerNameConfig(TrainerType.VETERAN), @@ -111,7 +111,7 @@ export const trainerNamePools = { [TrainerType.SMASHER]: ["Aspen","Elena","Mari","Amy","Lizzy"], [TrainerType.SNOW_WORKER]: [["Braden","Brendon","Colin","Conrad","Dillan","Gary","Gerardo","Holden","Jackson","Mason","Quentin","Willy","Noel","Arnold","Brady","Brand","Cairn","Cliff","Don","Eddie","Felix","Filipe","Glenn","Gus","Heath","Matthew","Patton","Rich","Rob","Ryan","Scott","Shelby","Sterling","Tyler","Victor","Zack","Friedrich","Herman","Isaac","Leo","Maynard","Mitchell","Morgann","Nathan","Niel","Pasqual","Paul","Tavarius","Tibor","Dimitri","Narek","Yusif","Frank","Jeff","Vaclav","Ovid","Francis","Keith","Russel","Sangon","Toway","Bomber","Chean","Demit","Hubor","Kebile","Laber","Ordo","Retay","Ronix","Wagel","Dobit","Kaster","Lobel","Releo","Saken","Rustix"],["Georgia","Sandra","Yvonne"]], [TrainerType.STRIKER]: ["Marco","Roberto","Tony"], - [TrainerType.STUDENT]: [["Alan","Billy","Chad","Danny","Dudley","Jack","Joe","Johnny","Kipp","Nate","Ricky","Tommy","Jerry","Paul","Ted","Chance","Esteban","Forrest","Harrison","Connor","Sherman","Torin","Travis","Al","Carter","Edgar","Jem","Sammy","Shane","Shayne","Alvin","Keston","Neil","Seymour","William","Carson","Clark","Nolan"],["Georgia","Karen","Meiko","Christine","Mackenzie","Tiera","Ann","Gina","Lydia","Marsha","Millie","Sally","Serena","Silvia","Alberta","Cassie","Mara","Rita","Georgie","Meena","Nitzel"]], + [TrainerType.SCHOOL_KID]: [["Alan","Billy","Chad","Danny","Dudley","Jack","Joe","Johnny","Kipp","Nate","Ricky","Tommy","Jerry","Paul","Ted","Chance","Esteban","Forrest","Harrison","Connor","Sherman","Torin","Travis","Al","Carter","Edgar","Jem","Sammy","Shane","Shayne","Alvin","Keston","Neil","Seymour","William","Carson","Clark","Nolan"],["Georgia","Karen","Meiko","Christine","Mackenzie","Tiera","Ann","Gina","Lydia","Marsha","Millie","Sally","Serena","Silvia","Alberta","Cassie","Mara","Rita","Georgie","Meena","Nitzel"]], [TrainerType.SWIMMER]: [["Berke","Cameron","Charlie","George","Harold","Jerome","Kirk","Mathew","Parker","Randall","Seth","Simon","Tucker","Austin","Barry","Chad","Cody","Darrin","David","Dean","Douglas","Franklin","Gilbert","Herman","Jack","Luis","Matthew","Reed","Richard","Rodney","Roland","Spencer","Stan","Tony","Clarence","Declan","Dominik","Harrison","Kevin","Leonardo","Nolen","Pete","Santiago","Axle","Braden","Finn","Garrett","Mymo","Reece","Samir","Toby","Adrian","Colton","Dillon","Erik","Evan","Francisco","Glenn","Kurt","Oscar","Ricardo","Sam","Sheltin","Troy","Vincent","Wade","Wesley","Duane","Elmo","Esteban","Frankie","Ronald","Tyson","Bart","Matt","Tim","Wright","Jeffery","Kyle","Alessandro","Estaban","Kieran","Ramses","Casey","Dakota","Jared","Kalani","Keoni","Lawrence","Logan","Robert","Roddy","Yasu","Derek","Jacob","Bruce","Clayton"],["Briana","Dawn","Denise","Diana","Elaine","Kara","Kaylee","Lori","Nicole","Nikki","Paula","Susie","Wendy","Alice","Beth","Beverly","Brenda","Dana","Debra","Grace","Jenny","Katie","Laurel","Linda","Missy","Sharon","Tanya","Tara","Tisha","Carlee","Imani","Isabelle","Kyla","Sienna","Abigail","Amara","Anya","Connie","Maria","Melissa","Nora","Shirley","Shania","Tiffany","Aubree","Cassandra","Claire","Crystal","Erica","Gabrielle","Haley","Jessica","Joanna","Lydia","Mallory","Mary","Miranda","Paige","Sophia","Vanessa","Chelan","Debbie","Joy","Kendra","Leona","Mina","Caroline","Joyce","Larissa","Rebecca","Tyra","Dara","Desiree","Kaoru","Ruth","Coral","Genevieve","Isla","Marissa","Romy","Sheryl","Alexandria","Alicia","Chelsea","Jade","Kelsie","Laura","Portia","Shelby","Sara","Tiare","Kyra","Natasha","Layla","Scarlett","Cora"]], [TrainerType.TWINS]: ["Amy & May","Jo & Zoe","Meg & Peg","Ann & Anne","Lea & Pia","Amy & Liv","Gina & Mia","Miu & Yuki","Tori & Tia","Eli & Anne","Jen & Kira","Joy & Meg","Kiri & Jan","Miu & Mia","Emma & Lil","Liv & Liz","Teri & Tia","Amy & Mimi","Clea & Gil","Day & Dani","Kay & Tia","Tori & Til","Saya & Aya","Emy & Lin","Kumi & Amy","Mayo & May","Ally & Amy","Lia & Lily","Rae & Ula","Sola & Ana","Tara & Val","Faith & Joy","Nana & Nina"], [TrainerType.VETERAN]: [["Armando","Brenden","Brian","Clayton","Edgar","Emanuel","Grant","Harlan","Terrell","Arlen","Chester","Hugo","Martell","Ray","Shaun","Abraham","Carter","Claude","Jerry","Lucius","Murphy","Rayne","Ron","Sinan","Sterling","Vincent","Zach","Gerard","Gilles","Louis","Timeo","Akira","Don","Eric","Harry","Leon","Roger","Angus","Aristo","Brone","Johnny"],["Julia","Karla","Kim","Sayuri","Tiffany","Cathy","Cecile","Chloris","Denae","Gina","Maya","Oriana","Portia","Rhona","Rosaline","Catrina","Inga","Trisha","Heather","Lynn","Sheri","Alonsa","Ella","Leticia","Kiara"]], diff --git a/src/field/trainer.ts b/src/field/trainer.ts index 4a7458652c4..9213dc0135d 100644 --- a/src/field/trainer.ts +++ b/src/field/trainer.ts @@ -10,6 +10,8 @@ import { PersistentModifier } from "../modifier/modifier"; import { trainerNamePools } from "../data/trainer-names"; import { ArenaTagType } from "#app/data/enums/arena-tag-type"; import { ArenaTag, ArenaTagSide, ArenaTrapTag } from "#app/data/arena-tag"; +import {getIsInitialized, initI18n} from "#app/plugins/i18n"; +import i18next from "i18next"; export enum TrainerVariant { DEFAULT, @@ -97,9 +99,16 @@ export default class Trainer extends Phaser.GameObjects.Container { getName(trainerSlot: TrainerSlot = TrainerSlot.NONE, includeTitle: boolean = false): string { let name = this.config.getTitle(trainerSlot, this.variant); let title = includeTitle && this.config.title ? this.config.title : null; + + if (this.name) { if (includeTitle) - title = name; + + // Check if i18n is initialized + if (!getIsInitialized()) { + initI18n() + } + title = i18next.t(`trainerClasses:${name.toLowerCase().replace(/\s/g, '_')}`); if (!trainerSlot) { name = this.name; if (this.partnerName) @@ -107,6 +116,7 @@ export default class Trainer extends Phaser.GameObjects.Container { } else name = trainerSlot === TrainerSlot.TRAINER ? this.name : this.partnerName || this.name; } + return title ? `${title} ${name}` : name; } diff --git a/src/locales/de/config.ts b/src/locales/de/config.ts index 72200a5141c..c9a58bca1ea 100644 --- a/src/locales/de/config.ts +++ b/src/locales/de/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { splashMessages } from "./splash-messages" @@ -32,9 +33,12 @@ export const deConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, splashMessages: splashMessages, nature: nature, growth: growth, modifierType: modifierType, -} \ No newline at end of file +} diff --git a/src/locales/de/trainers.ts b/src/locales/de/trainers.ts new file mode 100644 index 00000000000..b2a74a8e92f --- /dev/null +++ b/src/locales/de/trainers.ts @@ -0,0 +1,221 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Top Vier", + "gym_leader": "Arenaleiter", + "gym_leader_female": "Arenaleiterin", + "champion": "Champion", + "rival": "Rivale", + "professor": "Professor", + "frontier_brain": "Kampfkoryphäen", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Ass-Trainer", + "ace_trainer_female": "Ass-Trainerin", + "artist": "Künstler", + "artist_female": "Künstlerin", + "backers": "Anhänger", + "backpacker": "Backpacker", + "backpacker_female": "Backpackerin", + "baker": "Bäckerin", + "battle_girl": "Kämpferin", + "beauty": "Schönheit", + "biker": "Rowdy", + "black_belt": "Schwarzgurt", + "breeder": "Pokémon Züchter", + "breeder_female": "Pokémon Züchterin", + "clerk": "Angestellter", + "clerk_female": "Angestellte", + "cyclist": "Biker", + "cyclist_female": "Bikerin", + "dancer": "Tänzer", + "dancer_female": "Tänzerin", + "depot_agent": "Bahnangestellter", + "doctor": "Arzt", + "doctor_female": "Ärztin", + "fishermen": "Angler", + "fishermen_female": "Angler", // Seems to be the same in german but exists in other languages like italian + "guitarist": "Gitarrist", + "guitarist_female": "Gitarristin", + "harlequin": "Kasper", + "hiker": "Wanderer", + "hooligans": "Rabauken", + "hoopster": "Basketballer", + "infielder": "Baseballer", + "janitor": "Hausmeister", + "lady": "Lady", + "lass": "Göre", + "linebacker": "Footballer", + "maid": "Zofe", + "madame": "Madam", + "musican": "Musiker", + "hex_maniac": "Hexe", + "nurse": "Pflegerin", + "nursery_aide": "Erzieherin", + "officer": "Polizist", + "parasol_lady": "Schirmdame", + "pilot": "Pilot", + "pokefan": "Pokéfan", + "preschooler": "Vorschüler", + "preschooler_female": "Vorschülerin", + "psychic": "Seher", + "psychic_female": "Seherin", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Schnösel", + "roughneck": "Raufbold", + "scientist": "Forscher", + "scientist_female": "Forscherin", + "smasher": "Tennis-Ass", + "snow_worker": "Schneearbeiter", // There is a trainer type for this but no actual trainer class? They seem to be just workers but dressed differently + "snow_worker_female": "Schneearbeiterin", + "striker": "Fußballer", + "school_kid": "Schulkind", + "school_kid_female": "Schulkind", // Same in german but different in italian + "swimmer": "Schwimmer", + "swimmer_female": "Schwimmerin", + "twins": "Zwillinge", + "veteran": "Veteran", + "veteran_female": "Veteran", // same in german, different in other languages + "waiter": "Servierer", + "waitress": "Serviererin", + "worker": "Arbeiter", + "worker_female": "Arbeiterin", + "youngster": "Knirps" + + +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Rocko", + "misty": "Misty", + "lt_surge": "Major Bob", + "erika": "Erika", + "janine": "Janina", + "sabrina": "Sabrina", + "blaine": "Pyro", + "giovanni": "Giovanni", + "falkner": "Falk", + "bugsy": "Kai", + "whitney": "Bianka", + "morty": "Jens", + "chuck": "Hartwig", + "jasmine": "Jasmin", + "pryce": "Norbert", + "clair": "Sandra", + "roxanne": "Felizia", + "brawly": "Kamillo", + "wattson": "Walter", + "flannery": "Flavia", + "norman": "Norman", + "winona": "Wibke", + "tate": "Ben", + "liza": "Svenja", + "juan": "Juan", + "roark": "Veit", + "gardenia": "Silvana", + "maylene": "Hilda", + "crasher_wake": "Wellenbrecher Marinus", + "fantina": "Lamina", + "byron": "Adam", + "candice": "Frida", + "volkner": "Volkner", + "cilan": "Benny", + "chili": "Maik", + "cress": "Colin", + "cheren": "Cheren", + "lenora": "Aloe", + "roxie": "Mica", + "burgh": "Artie", + "elesa": "Kamilla", + "clay": "Turner", + "skyla": "Géraldine", + "brycen": "Sandro", + "drayden": "Lysander", + "marlon": "Benson", + "viola": "Viola", + "grant": "Lino", + "korrina": "Connie", + "ramos": "Amaro", + "clemont": "Citro", + "valerie": "Valerie", + "olympia": "Astrid", + "wulfric": "Galantho", + "milo": "Yarro", + "nessa": "Kate", + "kabu": "Kabu", + "bea": "Saida", + "allister": "Nio", + "opal": "Papella", + "bede": "Betys", + "gordie": "Mac", + "melony": "Mel", + "piers": "Nezz", + "marnie": "Mary", + "raihan": "Roy", + "katy": "Ronah", + "brassius": "Colzo", + "iono": "Enigmara", + "kofu": "Kombu", + "larry": "Aoki", + "ryme": "Etta", + "tulip": "Tulia", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agathe", + "lance": "Siegfried", + "will": "Willi", + "koga": "Koga", + "karen": "Melanie", + "sidney": "Ulrich", + "phoebe": "Antonia", + "glacia": "Frosina", + "drake": "Dragan", + "aaron": "Herbaro", + "bertha": "Teresa", + "flint": "Ignaz", + "lucian": "Lucian", + "shauntal": "Anissa", + "marshal": "Eugen", + "grimsley": "Astor", + "caitlin": "Kattlea", + "malva": "Pachira", + "siebold": "Narcisse", + "wikstrom": "Thymelot", + "drasna": "Dracena", + "hala": "Hala", + "molayne": "Marlon", + "olivia": "Mayla", + "acerola": "Lola", + "kahili": "Kahili", + "rika": "Cay", + "poppy": "Poppy", + "larry_elite": "Aoki", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Sinius", + "crispin": "Matt", + "amarys": "Erin", + "lacey": "Tara", + "drayton": "Levy", + "blue": "Blau", + "red": "Rot", + "lance_champion": "Siegfried", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Troy", + "wallace": "Wassili", + "cynthia": "Cynthia", + "alder": "Lauro", + "iris": "Lilia", + "diantha": "Diantha", + "hau": "Tali", + "geeta": "Sagaria", + "nemona": "Nemila", + "kieran": "Jo", + "leon": "Delion", + "rival": "Finn", + "rival_female": "Ivy", +} as const; \ No newline at end of file diff --git a/src/locales/en/config.ts b/src/locales/en/config.ts index 295c3ff5c33..a5d207da932 100644 --- a/src/locales/en/config.ts +++ b/src/locales/en/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,10 +34,13 @@ export const enConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, modifierType: modifierType, -} \ No newline at end of file +} diff --git a/src/locales/en/trainers.ts b/src/locales/en/trainers.ts new file mode 100644 index 00000000000..a63b06242f9 --- /dev/null +++ b/src/locales/en/trainers.ts @@ -0,0 +1,219 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Elite Four", + "gym_leader": "Gym Leader", + "gym_leader_female": "Gym Leader", + "champion": "Champion", + "rival": "Rival", + "professor": "Professor", + "frontier_brain": "Frontier Brain", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Ace Trainer", + "ace_trainer_female": "Ace Trainer", + "artist": "Artist", + "artist_female": "Artist", + "backers": "Backers", + "backpacker": "Backpacker", + "backpacker_female": "Backpacker", + "baker": "Baker", + "battle_girl": "Battle Girl", + "beauty": "Beauty", + "biker": "Biker", + "black_belt": "Black Belt", + "breeder": "Breeder", + "breeder_female": "Breeder", + "clerk": "Clerk", + "clerk_female": "Clerk", + "cyclist": "Cyclist", + "cyclist_female": "Cyclist", + "dancer": "Dancer", + "dancer_female": "Dancer", + "depot_agent": "Depot Agent", + "doctor": "Doctor", + "doctor_female": "Doctor", + "fishermen": "Fishermen", + "fishermen_female": "Fishermen", + "guitarist": "Guitarist", + "guitarist_female": "Guitarist", + "harlequin": "Harlequin", + "hiker": "Hiker", + "hooligans": "Hooligans", + "hoopster": "Hoopster", + "infielder": "Infielder", + "janitor": "Janitor", + "lady": "Lady", + "lass": "Lass", + "linebacker": "Linebacker", + "maid": "Maid", + "madame": "Madame", + "musican": "Musician", + "hex_maniac": "Hex Maniac", + "nurse": "Nurse", + "nursery_aide": "Nursery Aide", + "officer": "Officer", + "parasol_lady": "Parasol Lady", + "pilot": "Pilot", + "pokefan": "Poké Fan", + "preschooler": "Preschooler", + "preschooler_female": "Preschooler", + "psychic": "Psychic", + "psychic_female": "Psychic", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Rich Boy", + "roughneck": "Roughneck", + "scientist": "Scientist", + "scientist_female": "Scientist", + "smasher": "Smasher", + "snow_worker": "Snow Worker", + "snow_worker_female": "Snow Worker", + "striker": "Striker", + "school_kid": "School Kid", + "school_kid_female": "School Kid", + "swimmer": "Swimmer", + "swimmer_female": "Swimmer", + "twins": "Twins", + "veteran": "Veteran", + "veteran_female": "Veteran", + "waiter": "Waiter", + "waitress": "Waitress", + "worker": "Worker", + "worker_female": "Worker", + "youngster": "Youngster" +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Brock", + "misty": "Misty", + "lt_surge": "Lt Surge", + "erika": "Erika", + "janine": "Janine", + "sabrina": "Sabrina", + "blaine": "Blaine", + "giovanni": "Giovanni", + "falkner": "Falkner", + "bugsy": "Bugsy", + "whitney": "Whitney", + "morty": "Morty", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Pryce", + "clair": "Clair", + "roxanne": "Roxanne", + "brawly": "Brawly", + "wattson": "Wattson", + "flannery": "Flannery", + "norman": "Norman", + "winona": "Winona", + "tate": "Tate", + "liza": "Liza", + "juan": "Juan", + "roark": "Roark", + "gardenia": "Gardenia", + "maylene": "Maylene", + "crasher_wake": "Crasher Wake", + "fantina": "Fantina", + "byron": "Byron", + "candice": "Candice", + "volkner": "Volkner", + "cilan": "Cilan", + "chili": "Chili", + "cress": "Cress", + "cheren": "Cheren", + "lenora": "Lenora", + "roxie": "Roxie", + "burgh": "Burgh", + "elesa": "Elesa", + "clay": "Clay", + "skyla": "Skyla", + "brycen": "Brycen", + "drayden": "Drayden", + "marlon": "Marlon", + "viola": "Viola", + "grant": "Grant", + "korrina": "Korrina", + "ramos": "Ramos", + "clemont": "Clemont", + "valerie": "Valerie", + "olympia": "Olympia", + "wulfric": "Wulfric", + "milo": "Milo", + "nessa": "Nessa", + "kabu": "Kabu", + "bea": "Bea", + "allister": "Allister", + "opal": "Opal", + "bede": "Bede", + "gordie": "Gordie", + "melony": "Melony", + "piers": "Piers", + "marnie": "Marnie", + "raihan": "Raihan", + "katy": "Katy", + "brassius": "Brassius", + "iono": "Iono", + "kofu": "Kofu", + "larry": "Larry", + "ryme": "Ryme", + "tulip": "Tulip", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agatha", + "lance": "Lance", + "will": "Will", + "koga": "Koga", + "karen": "Karen", + "sidney": "Sidney", + "phoebe": "Phoebe", + "glacia": "Glacia", + "drake": "Drake", + "aaron": "Aaron", + "bertha": "Bertha", + "flint": "Flint", + "lucian": "Lucian", + "shauntal": "Shauntal", + "marshal": "Marshal", + "grimsley": "Grimsley", + "caitlin": "Caitlin", + "malva": "Malva", + "siebold": "Siebold", + "wikstrom": "Wikstrom", + "drasna": "Drasna", + "hala": "Hala", + "molayne": "Molayne", + "olivia": "Olivia", + "acerola": "Acerola", + "kahili": "Kahili", + "rika": "Rika", + "poppy": "Poppy", + "larry_elite": "Larry", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassel", + "crispin": "Crispin", + "amarys": "Amarys", + "lacey": "Lacey", + "drayton": "Drayton", + "blue": "Blue", + "red": "Red", + "lance_champion": "Lance", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Steven", + "wallace": "Wallace", + "cynthia": "Cynthia", + "alder": "Alder", + "iris": "Iris", + "diantha": "Diantha", + "hau": "Hau", + "geeta": "Geeta", + "nemona": "Nemona", + "kieran": "Kieran", + "leon": "Leon", + "rival": "Finn", + "rival_female": "Ivy", +} as const; diff --git a/src/locales/es/config.ts b/src/locales/es/config.ts index 6c36db3ed45..6aac47563ee 100644 --- a/src/locales/es/config.ts +++ b/src/locales/es/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,10 +34,13 @@ export const esConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, modifierType: modifierType, -} \ No newline at end of file +} diff --git a/src/locales/es/trainers.ts b/src/locales/es/trainers.ts new file mode 100644 index 00000000000..a63b06242f9 --- /dev/null +++ b/src/locales/es/trainers.ts @@ -0,0 +1,219 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Elite Four", + "gym_leader": "Gym Leader", + "gym_leader_female": "Gym Leader", + "champion": "Champion", + "rival": "Rival", + "professor": "Professor", + "frontier_brain": "Frontier Brain", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Ace Trainer", + "ace_trainer_female": "Ace Trainer", + "artist": "Artist", + "artist_female": "Artist", + "backers": "Backers", + "backpacker": "Backpacker", + "backpacker_female": "Backpacker", + "baker": "Baker", + "battle_girl": "Battle Girl", + "beauty": "Beauty", + "biker": "Biker", + "black_belt": "Black Belt", + "breeder": "Breeder", + "breeder_female": "Breeder", + "clerk": "Clerk", + "clerk_female": "Clerk", + "cyclist": "Cyclist", + "cyclist_female": "Cyclist", + "dancer": "Dancer", + "dancer_female": "Dancer", + "depot_agent": "Depot Agent", + "doctor": "Doctor", + "doctor_female": "Doctor", + "fishermen": "Fishermen", + "fishermen_female": "Fishermen", + "guitarist": "Guitarist", + "guitarist_female": "Guitarist", + "harlequin": "Harlequin", + "hiker": "Hiker", + "hooligans": "Hooligans", + "hoopster": "Hoopster", + "infielder": "Infielder", + "janitor": "Janitor", + "lady": "Lady", + "lass": "Lass", + "linebacker": "Linebacker", + "maid": "Maid", + "madame": "Madame", + "musican": "Musician", + "hex_maniac": "Hex Maniac", + "nurse": "Nurse", + "nursery_aide": "Nursery Aide", + "officer": "Officer", + "parasol_lady": "Parasol Lady", + "pilot": "Pilot", + "pokefan": "Poké Fan", + "preschooler": "Preschooler", + "preschooler_female": "Preschooler", + "psychic": "Psychic", + "psychic_female": "Psychic", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Rich Boy", + "roughneck": "Roughneck", + "scientist": "Scientist", + "scientist_female": "Scientist", + "smasher": "Smasher", + "snow_worker": "Snow Worker", + "snow_worker_female": "Snow Worker", + "striker": "Striker", + "school_kid": "School Kid", + "school_kid_female": "School Kid", + "swimmer": "Swimmer", + "swimmer_female": "Swimmer", + "twins": "Twins", + "veteran": "Veteran", + "veteran_female": "Veteran", + "waiter": "Waiter", + "waitress": "Waitress", + "worker": "Worker", + "worker_female": "Worker", + "youngster": "Youngster" +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Brock", + "misty": "Misty", + "lt_surge": "Lt Surge", + "erika": "Erika", + "janine": "Janine", + "sabrina": "Sabrina", + "blaine": "Blaine", + "giovanni": "Giovanni", + "falkner": "Falkner", + "bugsy": "Bugsy", + "whitney": "Whitney", + "morty": "Morty", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Pryce", + "clair": "Clair", + "roxanne": "Roxanne", + "brawly": "Brawly", + "wattson": "Wattson", + "flannery": "Flannery", + "norman": "Norman", + "winona": "Winona", + "tate": "Tate", + "liza": "Liza", + "juan": "Juan", + "roark": "Roark", + "gardenia": "Gardenia", + "maylene": "Maylene", + "crasher_wake": "Crasher Wake", + "fantina": "Fantina", + "byron": "Byron", + "candice": "Candice", + "volkner": "Volkner", + "cilan": "Cilan", + "chili": "Chili", + "cress": "Cress", + "cheren": "Cheren", + "lenora": "Lenora", + "roxie": "Roxie", + "burgh": "Burgh", + "elesa": "Elesa", + "clay": "Clay", + "skyla": "Skyla", + "brycen": "Brycen", + "drayden": "Drayden", + "marlon": "Marlon", + "viola": "Viola", + "grant": "Grant", + "korrina": "Korrina", + "ramos": "Ramos", + "clemont": "Clemont", + "valerie": "Valerie", + "olympia": "Olympia", + "wulfric": "Wulfric", + "milo": "Milo", + "nessa": "Nessa", + "kabu": "Kabu", + "bea": "Bea", + "allister": "Allister", + "opal": "Opal", + "bede": "Bede", + "gordie": "Gordie", + "melony": "Melony", + "piers": "Piers", + "marnie": "Marnie", + "raihan": "Raihan", + "katy": "Katy", + "brassius": "Brassius", + "iono": "Iono", + "kofu": "Kofu", + "larry": "Larry", + "ryme": "Ryme", + "tulip": "Tulip", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agatha", + "lance": "Lance", + "will": "Will", + "koga": "Koga", + "karen": "Karen", + "sidney": "Sidney", + "phoebe": "Phoebe", + "glacia": "Glacia", + "drake": "Drake", + "aaron": "Aaron", + "bertha": "Bertha", + "flint": "Flint", + "lucian": "Lucian", + "shauntal": "Shauntal", + "marshal": "Marshal", + "grimsley": "Grimsley", + "caitlin": "Caitlin", + "malva": "Malva", + "siebold": "Siebold", + "wikstrom": "Wikstrom", + "drasna": "Drasna", + "hala": "Hala", + "molayne": "Molayne", + "olivia": "Olivia", + "acerola": "Acerola", + "kahili": "Kahili", + "rika": "Rika", + "poppy": "Poppy", + "larry_elite": "Larry", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassel", + "crispin": "Crispin", + "amarys": "Amarys", + "lacey": "Lacey", + "drayton": "Drayton", + "blue": "Blue", + "red": "Red", + "lance_champion": "Lance", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Steven", + "wallace": "Wallace", + "cynthia": "Cynthia", + "alder": "Alder", + "iris": "Iris", + "diantha": "Diantha", + "hau": "Hau", + "geeta": "Geeta", + "nemona": "Nemona", + "kieran": "Kieran", + "leon": "Leon", + "rival": "Finn", + "rival_female": "Ivy", +} as const; diff --git a/src/locales/fr/config.ts b/src/locales/fr/config.ts index f6245f4eeaa..a2bb8430fba 100644 --- a/src/locales/fr/config.ts +++ b/src/locales/fr/config.ts @@ -15,10 +15,12 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { splashMessages } from "./splash-messages" import { weather } from "./weather"; + export const frConfig = { ability: ability, abilityTriggers: abilityTriggers, @@ -33,10 +35,14 @@ export const frConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, modifierType: modifierType, -} \ No newline at end of file +} + diff --git a/src/locales/fr/trainers.ts b/src/locales/fr/trainers.ts new file mode 100644 index 00000000000..761e3f62635 --- /dev/null +++ b/src/locales/fr/trainers.ts @@ -0,0 +1,219 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Conseil 4", + "gym_leader": "Champion d’Arène", + "gym_leader_female": "Championne d’Arène", + "champion": "Maitre·esse", //Written in gender-inclusive language in wait of a potential split of the entry + "rival": "Rival·e", //Written in gender-inclusive language in wait of a potential split of the entry + "professor": "Professeur·e", //Written in gender-inclusive language in wait of a potential split of the entry + "frontier_brain": "Meneur·euse de Zone", //Written in gender-inclusive language in wait of a potential split of the entry + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Topdresseur", + "ace_trainer_female": "Topdresseuse", + "artist": "Artiste", + "artist_female": "Artiste", + "backers": "Pompom Girls", + "backpacker": "Randonneur", + "backpacker_female": "Randonneuse", + "baker": "Boulangère", + "battle_girl": "Combattante", + "beauty": "Canon", + "biker": "Motard", + "black_belt": "Karatéka", + "breeder": "Éleveur", + "breeder_female": "Éleveuse", + "clerk": "Employé", + "clerk_female": "Employée", + "cyclist": "Cycliste", + "cyclist_female": "Cycliste", + "dancer": "Danseur", + "dancer_female": "Danseuse", + "depot_agent": "Cheminot", + "doctor": "Docteur", + "doctor_female": "Docteure", + "fishermen": "Pêcheur", + "fishermen_female": "Pêcheuse", + "guitarist": "Guitariste", + "guitarist_female": "Guitariste", + "harlequin": "Clown", + "hiker": "Montagnard", + "hooligans": "Loubards", + "hoopster": "Basketteur", + "infielder": "Baseballeur", + "janitor": "Nettoyeur", + "lady": "Mademoiselle", + "lass": "Fillette", + "linebacker": "Quaterback", + "maid": "Gouvernante", + "madame": "Mondaine", + "musican": "Musicien", + "hex_maniac": "Hex Maniac", + "nurse": " Infirmière", + "nursery_aide": "Institutrice", + "officer": "Policier", + "parasol_lady": "Sœur Parasol", + "pilot": "Pilote", + "pokefan": "Pokéfan", + "preschooler": "Petit", + "preschooler_female": "Petite", + "psychic": "Kinésiste", + "psychic_female": "Kinésiste", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Richard", + "roughneck": "Loubard", + "scientist": "Scientifique", + "scientist_female": "Scientifique", + "smasher": "Tenniswoman", + "snow_worker": "Ouvrier Alpin", + "snow_worker_female": "Ouvrière Alpine", + "striker": "Footballeur", + "school_kid": "Élève", + "school_kid_female": "Élève", + "swimmer": "Nageur", + "swimmer_female": "Nageuse", + "twins": "Jumelles", + "veteran": "Vénérable", + "veteran_female": "Vénérable", + "waiter": "Serveur", + "waitress": "Serveuse", + "worker": "Ouvrier", + "worker_female": "Ouvrière", + "youngster": "Gamin" +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Pierre", + "misty": "Ondine", + "lt_surge": "Major Bob", + "erika": "Erika", + "janine": "Jeannine", + "sabrina": "Morgane", + "blaine": "Auguste", + "giovanni": "Giovanni", + "falkner": "Albert", + "bugsy": "Hector", + "whitney": "Blanche", + "morty": "Mortimer", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Frédo", + "clair": "Sandra", + "roxanne": "Roxanne", + "brawly": "Bastien", + "wattson": "Voltère", + "flannery": "Adriane", + "norman": "Norman", + "winona": "Alizée", + "tate": "Lévy", + "liza": "Tatia", + "juan": "Juan", + "roark": "Pierrick", + "gardenia": "Flo", + "maylene": "Mélina", + "crasher_wake": "Lovis", + "fantina": "Kiméra", + "byron": "Charles", + "candice": "Gladys", + "volkner": "Tanguy", + "cilan": "Rachid", + "chili": "Armando", + "cress": "Noa", + "cheren": "Tcheren", + "lenora": "Aloé", + "roxie": "Strykna", + "burgh": "Artie", + "elesa": "Inezia", + "clay": "Bardane", + "skyla": "Carolina", + "brycen": "Zhu", + "drayden": "Watson", + "marlon": "Amana", + "viola": "Violette", + "grant": "Lino", + "korrina": "Cornélia", + "ramos": "Amaro", + "clemont": "Lem", + "valerie": "Valériane", + "olympia": "Astera", + "wulfric": "Urup", + "milo": "Percy", + "nessa": "Donna", + "kabu": "Kabu", + "bea": "Faïza", + "allister": "Alistair", + "opal": "Sally", + "bede": "Travis", + "gordie": "Chaz", + "melony": "Lona", + "piers": "Peterson", + "marnie": "Rosemary", + "raihan": "Roy", + "katy": "Éra", + "brassius": "Colza", + "iono": "Mashynn", + "kofu": "Kombu", + "larry": "Okuba", + "ryme": "Laïm", + "tulip": "Tully", + "grusha": "Grusha", + "lorelei": "Olga", + "bruno": "Aldo", + "agatha": "Agatha", + "lance": "Peter", + "will": "Clément", + "koga": "Koga", + "karen": "Marion", + "sidney": "Damien", + "phoebe": "Spectra", + "glacia": "Glacia", + "drake": "Aragon", + "aaron": "Aaron", + "bertha": "Terry", + "flint": "Adrien", + "lucian": "Lucio", + "shauntal": "Anis", + "marshal": "Kunz", + "grimsley": "Pieris", + "caitlin": "Percila", + "malva": "Malva", + "siebold": "Narcisse", + "wikstrom": "Tileo", + "drasna": "Dracéna", + "hala": "Pectorius", + "molayne": "Molène", + "olivia": "Alyxia", + "acerola": "Margie", + "kahili": "Kahili", + "rika": "Cayenn", + "poppy": "Popi", + "larry_elite": "Okuba", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassa", + "crispin": "Rubépin", + "amarys": "Nérine", + "lacey": "Taro", + "drayton": "Irido", + "blue": "Blue", + "red": "Red", + "lance_champion": "Peter", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Pierre Rochard", + "wallace": "Marc", + "cynthia": "Cynthia", + "alder": "Goyah", + "iris": "Iris", + "diantha": "Dianthéa", + "hau": "Tili", + "geeta": "Alisma", + "nemona": "Menzi", + "kieran": "Kass", + "leon": "Tarak", + "rival": "Gwenaël", //Male breton name, a celtic language spoken in Brittany (France) and related to the word for "white" (gwenn). Finn meaning is also "white" in irish/goidelic which are also celtic languages. + "rival_female": "Papina", //Litteral translation of ivy, also used as Female name in a North-American indigenous language +} as const; diff --git a/src/locales/it/config.ts b/src/locales/it/config.ts index 11b1b9e5628..baa252bcb16 100644 --- a/src/locales/it/config.ts +++ b/src/locales/it/config.ts @@ -15,6 +15,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { splashMessages } from "./splash-messages" import { weather } from "./weather"; @@ -33,10 +34,13 @@ export const itConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, splashMessages: splashMessages, nature: nature, growth: growth, weather: weather, modifierType: modifierType, -} \ No newline at end of file +} diff --git a/src/locales/it/trainers.ts b/src/locales/it/trainers.ts new file mode 100644 index 00000000000..a63b06242f9 --- /dev/null +++ b/src/locales/it/trainers.ts @@ -0,0 +1,219 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Elite Four", + "gym_leader": "Gym Leader", + "gym_leader_female": "Gym Leader", + "champion": "Champion", + "rival": "Rival", + "professor": "Professor", + "frontier_brain": "Frontier Brain", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Ace Trainer", + "ace_trainer_female": "Ace Trainer", + "artist": "Artist", + "artist_female": "Artist", + "backers": "Backers", + "backpacker": "Backpacker", + "backpacker_female": "Backpacker", + "baker": "Baker", + "battle_girl": "Battle Girl", + "beauty": "Beauty", + "biker": "Biker", + "black_belt": "Black Belt", + "breeder": "Breeder", + "breeder_female": "Breeder", + "clerk": "Clerk", + "clerk_female": "Clerk", + "cyclist": "Cyclist", + "cyclist_female": "Cyclist", + "dancer": "Dancer", + "dancer_female": "Dancer", + "depot_agent": "Depot Agent", + "doctor": "Doctor", + "doctor_female": "Doctor", + "fishermen": "Fishermen", + "fishermen_female": "Fishermen", + "guitarist": "Guitarist", + "guitarist_female": "Guitarist", + "harlequin": "Harlequin", + "hiker": "Hiker", + "hooligans": "Hooligans", + "hoopster": "Hoopster", + "infielder": "Infielder", + "janitor": "Janitor", + "lady": "Lady", + "lass": "Lass", + "linebacker": "Linebacker", + "maid": "Maid", + "madame": "Madame", + "musican": "Musician", + "hex_maniac": "Hex Maniac", + "nurse": "Nurse", + "nursery_aide": "Nursery Aide", + "officer": "Officer", + "parasol_lady": "Parasol Lady", + "pilot": "Pilot", + "pokefan": "Poké Fan", + "preschooler": "Preschooler", + "preschooler_female": "Preschooler", + "psychic": "Psychic", + "psychic_female": "Psychic", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Rich Boy", + "roughneck": "Roughneck", + "scientist": "Scientist", + "scientist_female": "Scientist", + "smasher": "Smasher", + "snow_worker": "Snow Worker", + "snow_worker_female": "Snow Worker", + "striker": "Striker", + "school_kid": "School Kid", + "school_kid_female": "School Kid", + "swimmer": "Swimmer", + "swimmer_female": "Swimmer", + "twins": "Twins", + "veteran": "Veteran", + "veteran_female": "Veteran", + "waiter": "Waiter", + "waitress": "Waitress", + "worker": "Worker", + "worker_female": "Worker", + "youngster": "Youngster" +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Brock", + "misty": "Misty", + "lt_surge": "Lt Surge", + "erika": "Erika", + "janine": "Janine", + "sabrina": "Sabrina", + "blaine": "Blaine", + "giovanni": "Giovanni", + "falkner": "Falkner", + "bugsy": "Bugsy", + "whitney": "Whitney", + "morty": "Morty", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Pryce", + "clair": "Clair", + "roxanne": "Roxanne", + "brawly": "Brawly", + "wattson": "Wattson", + "flannery": "Flannery", + "norman": "Norman", + "winona": "Winona", + "tate": "Tate", + "liza": "Liza", + "juan": "Juan", + "roark": "Roark", + "gardenia": "Gardenia", + "maylene": "Maylene", + "crasher_wake": "Crasher Wake", + "fantina": "Fantina", + "byron": "Byron", + "candice": "Candice", + "volkner": "Volkner", + "cilan": "Cilan", + "chili": "Chili", + "cress": "Cress", + "cheren": "Cheren", + "lenora": "Lenora", + "roxie": "Roxie", + "burgh": "Burgh", + "elesa": "Elesa", + "clay": "Clay", + "skyla": "Skyla", + "brycen": "Brycen", + "drayden": "Drayden", + "marlon": "Marlon", + "viola": "Viola", + "grant": "Grant", + "korrina": "Korrina", + "ramos": "Ramos", + "clemont": "Clemont", + "valerie": "Valerie", + "olympia": "Olympia", + "wulfric": "Wulfric", + "milo": "Milo", + "nessa": "Nessa", + "kabu": "Kabu", + "bea": "Bea", + "allister": "Allister", + "opal": "Opal", + "bede": "Bede", + "gordie": "Gordie", + "melony": "Melony", + "piers": "Piers", + "marnie": "Marnie", + "raihan": "Raihan", + "katy": "Katy", + "brassius": "Brassius", + "iono": "Iono", + "kofu": "Kofu", + "larry": "Larry", + "ryme": "Ryme", + "tulip": "Tulip", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agatha", + "lance": "Lance", + "will": "Will", + "koga": "Koga", + "karen": "Karen", + "sidney": "Sidney", + "phoebe": "Phoebe", + "glacia": "Glacia", + "drake": "Drake", + "aaron": "Aaron", + "bertha": "Bertha", + "flint": "Flint", + "lucian": "Lucian", + "shauntal": "Shauntal", + "marshal": "Marshal", + "grimsley": "Grimsley", + "caitlin": "Caitlin", + "malva": "Malva", + "siebold": "Siebold", + "wikstrom": "Wikstrom", + "drasna": "Drasna", + "hala": "Hala", + "molayne": "Molayne", + "olivia": "Olivia", + "acerola": "Acerola", + "kahili": "Kahili", + "rika": "Rika", + "poppy": "Poppy", + "larry_elite": "Larry", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassel", + "crispin": "Crispin", + "amarys": "Amarys", + "lacey": "Lacey", + "drayton": "Drayton", + "blue": "Blue", + "red": "Red", + "lance_champion": "Lance", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Steven", + "wallace": "Wallace", + "cynthia": "Cynthia", + "alder": "Alder", + "iris": "Iris", + "diantha": "Diantha", + "hau": "Hau", + "geeta": "Geeta", + "nemona": "Nemona", + "kieran": "Kieran", + "leon": "Leon", + "rival": "Finn", + "rival_female": "Ivy", +} as const; diff --git a/src/locales/pt_BR/trainers.ts b/src/locales/pt_BR/trainers.ts new file mode 100644 index 00000000000..b1f56e70ae4 --- /dev/null +++ b/src/locales/pt_BR/trainers.ts @@ -0,0 +1,219 @@ +import { SimpleTranslationEntries } from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Elite dos Quatro", + "gym_leader": "Líder de Ginásio", + "gym_leader_female": "Líder de Ginásio", + "champion": "Campeão", + "rival": "Rival", + "professor": "Professor", + "frontier_brain": "Cérebro da Fronteira", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Trinador Ás", + "ace_trainer_female": "Trinadora Ás", + "artist": "Artista", + "artist_female": "Artista", + "backers": "Torcedores", + "backpacker": "Mochileiro", + "backpacker_female": "Mochileira", + "baker": "Padeira", + "battle_girl": "Lutadora", + "beauty": "Modelo", + "biker": "Motoqueiro", + "black_belt": "Faixa Preta", + "breeder": "Criador", + "breeder_female": "Criadora", + "clerk": "Funcionário", + "clerk_female": "Funcionária", + "cyclist": "Ciclista", + "cyclist_female": "Ciclista", + "dancer": "Dançarino", + "dancer_female": "Dançarina", + "depot_agent": "Ferroviário", + "doctor": "Doutor", + "doctor_female": "Doutora", + "fishermen": "Pescador", + "fishermen_female": "Pescadora", + "guitarist": "Guitarrista", + "guitarist_female": "Guitarrista", + "harlequin": "Arlequim", + "hiker": "Montanhista", + "hooligans": "Bandoleiro", + "hoopster": "Jogador de basquete", + "infielder": "Jogador de baseball", + "janitor": "Faxineiro", + "lady": "Dama", + "lass": "Senhorita", + "linebacker": "Zagueiro", + "maid": "Doméstica", + "madame": "Madame", + "musican": "Músico", + "hex_maniac": "Ocultista", + "nurse": "Enfermeira", + "nursery_aide": "Professora do Berçário", + "officer": "Policial", + "parasol_lady": "Moça de Sombrinha", + "pilot": "Piloto", + "pokefan": "Pokefã", + "preschooler": "Menino do Prezinho", + "preschooler_female": "Menina do Prezinho", + "psychic": "Médium", + "psychic_female": "Médium", + "ranger": "Guarda", + "rich": "Cavalheira", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Riquinho", + "roughneck": "Arruaceiro", + "scientist": "Cientista", + "scientist_female": "Cientista", + "smasher": "Tenista", + "snow_worker": "Operário da Neve", + "snow_worker_female": "Operária da Neve", + "striker": "Atacante", + "school_kid": "Estudante", + "school_kid_female": "Estudante", + "swimmer": "Nadador", + "swimmer_female": "Nadadora", + "twins": "Gêmeos", + "veteran": "Veterano", + "veteran_female": "Veterana", + "waiter": "Garçom", + "waitress": "Garçonete", + "worker": "Operário", + "worker_female": "Operária", + "youngster": "Jovem", +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Brock", + "misty": "Misty", + "lt_surge": "Ten. Surge", + "erika": "Erika", + "janine": "Janine", + "sabrina": "Sabrina", + "blaine": "Blaine", + "giovanni": "Giovanni", + "falkner": "Falkner", + "bugsy": "Bugsy", + "whitney": "Whitney", + "morty": "Morty", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Pryce", + "clair": "Clair", + "roxanne": "Roxanne", + "brawly": "Brawly", + "wattson": "Wattson", + "flannery": "Flannery", + "norman": "Norman", + "winona": "Winona", + "tate": "Tate", + "liza": "Liza", + "juan": "Juan", + "roark": "Roark", + "gardenia": "Gardenia", + "maylene": "Maylene", + "crasher_wake": "Demolidor Wake", + "fantina": "Fantina", + "byron": "Byron", + "candice": "Candice", + "volkner": "Volkner", + "cilan": "Cilan", + "chili": "Chili", + "cress": "Cress", + "cheren": "Cheren", + "lenora": "Lenora", + "roxie": "Roxie", + "burgh": "Burgh", + "elesa": "Elesa", + "clay": "Clay", + "skyla": "Skyla", + "brycen": "Brycen", + "drayden": "Drayden", + "marlon": "Marlon", + "viola": "Viola", + "grant": "Grant", + "korrina": "Korrina", + "ramos": "Ramos", + "clemont": "Clemont", + "valerie": "Valerie", + "olympia": "Olympia", + "wulfric": "Wulfric", + "milo": "Milo", + "nessa": "Nessa", + "kabu": "Kabu", + "bea": "Bea", + "allister": "Allister", + "opal": "Opal", + "bede": "Bede", + "gordie": "Gordie", + "melony": "Melony", + "piers": "Piers", + "marnie": "Marnie", + "raihan": "Raihan", + "katy": "Katy", + "brassius": "Brassius", + "iono": "Iono", + "kofu": "Kofu", + "larry": "Larry", + "ryme": "Ryme", + "tulip": "Tulip", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agatha", + "lance": "Lance", + "will": "Will", + "koga": "Koga", + "karen": "Karen", + "sidney": "Sidney", + "phoebe": "Phoebe", + "glacia": "Glacia", + "drake": "Drake", + "aaron": "Aaron", + "bertha": "Bertha", + "flint": "Flint", + "lucian": "Lucian", + "shauntal": "Shauntal", + "marshal": "Marshal", + "grimsley": "Grimsley", + "caitlin": "Caitlin", + "malva": "Malva", + "siebold": "Siebold", + "wikstrom": "Wikstrom", + "drasna": "Drasna", + "hala": "Hala", + "molayne": "Molayne", + "olivia": "Olivia", + "acerola": "Acerola", + "kahili": "Kahili", + "rika": "Rika", + "poppy": "Poppy", + "larry_elite": "Larry", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassel", + "crispin": "Crispin", + "amarys": "Amarys", + "lacey": "Lacey", + "drayton": "Drayton", + "blue": "Blue", + "red": "Red", + "lance_champion": "Lance", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Steven", + "wallace": "Wallace", + "cynthia": "Cynthia", + "alder": "Alder", + "iris": "Iris", + "diantha": "Diantha", + "hau": "Hau", + "geeta": "Geeta", + "nemona": "Nemona", + "kieran": "Kieran", + "leon": "Leon", + "rival": "Finn", + "rival_female": "Ivy", +} as const; \ No newline at end of file diff --git a/src/locales/zh_CN/config.ts b/src/locales/zh_CN/config.ts index 11339dca4c8..957b1e7a482 100644 --- a/src/locales/zh_CN/config.ts +++ b/src/locales/zh_CN/config.ts @@ -11,6 +11,7 @@ import { pokemon } from "./pokemon"; import { pokemonStat } from "./pokemon-stat"; import { starterSelectUiHandler } from "./starter-select-ui-handler"; import { tutorial } from "./tutorial"; +import { titles,trainerClasses,trainerNames } from "./trainers"; import { nature } from "./nature"; import { weather } from "./weather"; import { modifierType } from "./modifier-type"; @@ -30,9 +31,13 @@ export const zhCnConfig = { pokemonStat: pokemonStat, pokemon: pokemon, starterSelectUiHandler: starterSelectUiHandler, + nature: nature, + titles: titles, + trainerClasses: trainerClasses, + trainerNames: trainerNames, tutorial: tutorial, nature: nature, growth: growth, weather: weather, modifierType: modifierType, -} \ No newline at end of file +} diff --git a/src/locales/zh_CN/trainers.ts b/src/locales/zh_CN/trainers.ts new file mode 100644 index 00000000000..2a9af843870 --- /dev/null +++ b/src/locales/zh_CN/trainers.ts @@ -0,0 +1,218 @@ +import {SimpleTranslationEntries} from "#app/plugins/i18n"; + +// Titles of special trainers like gym leaders, elite four, and the champion +export const titles: SimpleTranslationEntries = { + "elite_four": "Elite Four", + "gym_leader": "Gym Leader", + "gym_leader_female": "Gym Leader", + "champion": "Champion", + "rival": "Rival", + "professor": "Professor", + "frontier_brain": "Frontier Brain", + // Maybe if we add the evil teams we can add "Team Rocket" and "Team Aqua" etc. here as well as "Team Rocket Boss" and "Team Aqua Admin" etc. +} as const; + +// Titles of trainers like "Youngster" or "Lass" +export const trainerClasses: SimpleTranslationEntries = { + "ace_trainer": "Ace Trainer", + "ace_trainer_female": "Ace Trainer", + "artist": "Artist", + "artist_female": "Artist", + "backers": "Backers", + "backpacker": "Backpacker", + "backpacker_female": "Backpacker", + "baker": "Baker", + "battle_girl": "Battle Girl", + "beauty": "Beauty", + "biker": "Biker", + "black_belt": "Black Belt", + "breeder": "Breeder", + "breeder_female": "Breeder", + "clerk": "Clerk", + "clerk_female": "Clerk", + "cyclist": "Cyclist", + "cyclist_female": "Cyclist", + "dancer": "Dancer", + "dancer_female": "Dancer", + "depot_agent": "Depot Agent", + "doctor": "Doctor", + "doctor_female": "Doctor", + "fishermen": "Fishermen", + "fishermen_female": "Fishermen", + "guitarist": "Guitarist", + "guitarist_female": "Guitarist", + "harlequin": "Harlequin", + "hiker": "Hiker", + "hooligans": "Hooligans", + "hoopster": "Hoopster", + "infielder": "Infielder", + "janitor": "Janitor", + "lady": "Lady", + "lass": "Lass", + "linebacker": "Linebacker", + "maid": "Maid", + "madame": "Madame", + "musican": "Musician", + "hex_maniac": "Hex Maniac", + "nurse": "Nurse", + "nursery_aide": "Nursery Aide", + "officer": "Officer", + "parasol_lady": "Parasol Lady", + "pilot": "Pilot", + "pokefan": "Poké Fan", + "preschooler": "Preschooler", + "preschooler_female": "Preschooler", + "psychic": "Psychic", + "psychic_female": "Psychic", + "ranger": "Ranger", + "rich": "Gentleman", // Gentleman is the english name but the trainerType is rich + "rich_kid": "Rich Boy", + "roughneck": "Roughneck", + "scientist": "Scientist", + "scientist_female": "Scientist", + "smasher": "Smasher", + "snow_worker": "Snow Worker", + "snow_worker_female": "Snow Worker", + "striker": "Striker", + "school_kid": "School Kid", + "school_kid_female": "School Kid", + "swimmer": "Swimmer", + "swimmer_female": "Swimmer", + "twins": "Twins", + "veteran": "Veteran", + "veteran_female": "Veteran", + "waiter": "Waiter", + "waitress": "Waitress", + "worker": "Worker", + "worker_female": "Worker", + "youngster": "Youngster" +} as const; + +// Names of special trainers like gym leaders, elite four, and the champion +export const trainerNames: SimpleTranslationEntries = { + "brock": "Brock", + "misty": "Misty", + "lt_surge": "Lt Surge", + "erika": "Erika", + "janine": "Janine", + "sabrina": "Sabrina", + "blaine": "Blaine", + "giovanni": "Giovanni", + "falkner": "Falkner", + "bugsy": "Bugsy", + "whitney": "Whitney", + "morty": "Morty", + "chuck": "Chuck", + "jasmine": "Jasmine", + "pryce": "Pryce", + "clair": "Clair", + "roxanne": "Roxanne", + "brawly": "Brawly", + "wattson": "Wattson", + "flannery": "Flannery", + "norman": "Norman", + "winona": "Winona", + "tate": "Tate", + "liza": "Liza", + "juan": "Juan", + "roark": "Roark", + "gardenia": "Gardenia", + "maylene": "Maylene", + "crasher_wake": "Crasher Wake", + "fantina": "Fantina", + "byron": "Byron", + "candice": "Candice", + "volkner": "Volkner", + "cilan": "Cilan", + "chili": "Chili", + "cress": "Cress", + "cheren": "Cheren", + "lenora": "Lenora", + "roxie": "Roxie", + "burgh": "Burgh", + "elesa": "Elesa", + "clay": "Clay", + "skyla": "Skyla", + "brycen": "Brycen", + "drayden": "Drayden", + "marlon": "Marlon", + "viola": "Viola", + "grant": "Grant", + "korrina": "Korrina", + "ramos": "Ramos", + "clemont": "Clemont", + "valerie": "Valerie", + "olympia": "Olympia", + "wulfric": "Wulfric", + "milo": "Milo", + "nessa": "Nessa", + "kabu": "Kabu", + "bea": "Bea", + "allister": "Allister", + "opal": "Opal", + "bede": "Bede", + "gordie": "Gordie", + "melony": "Melony", + "piers": "Piers", + "marnie": "Marnie", + "raihan": "Raihan", + "katy": "Katy", + "brassius": "Brassius", + "iono": "Iono", + "kofu": "Kofu", + "larry": "Larry", + "ryme": "Ryme", + "tulip": "Tulip", + "grusha": "Grusha", + "lorelei": "Lorelei", + "bruno": "Bruno", + "agatha": "Agatha", + "lance": "Lance", + "will": "Will", + "koga": "Koga", + "karen": "Karen", + "sidney": "Sidney", + "phoebe": "Phoebe", + "glacia": "Glacia", + "drake": "Drake", + "aaron": "Aaron", + "bertha": "Bertha", + "flint": "Flint", + "lucian": "Lucian", + "shauntal": "Shauntal", + "marshal": "Marshal", + "grimsley": "Grimsley", + "caitlin": "Caitlin", + "malva": "Malva", + "siebold": "Siebold", + "wikstrom": "Wikstrom", + "drasna": "Drasna", + "hala": "Hala", + "molayne": "Molayne", + "olivia": "Olivia", + "acerola": "Acerola", + "kahili": "Kahili", + "rika": "Rika", + "poppy": "Poppy", + "larry_elite": "Larry", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "hassel": "Hassel", + "crispin": "Crispin", + "amarys": "Amarys", + "lacey": "Lacey", + "drayton": "Drayton", + "blue": "Blue", + "red": "Red", + "lance_champion": "Lance", // Does this really need to be an extra entry? (it is in trainer-type.ts so I added it here) + "steven": "Steven", + "wallace": "Wallace", + "cynthia": "Cynthia", + "alder": "Alder", + "iris": "Iris", + "diantha": "Diantha", + "hau": "Hau", + "geeta": "Geeta", + "nemona": "Nemona", + "kieran": "Kieran", + "leon": "Leon", + "rival": "Rival", +} as const; diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index 1e0363f1688..807e1a1b550 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -8,7 +8,6 @@ import { frConfig } from '#app/locales/fr/config.js'; import { itConfig } from '#app/locales/it/config.js'; import { ptBrConfig } from '#app/locales/pt_BR/config.js'; import { zhCnConfig } from '#app/locales/zh_CN/config.js'; - export interface SimpleTranslationEntries { [key: string]: string } @@ -52,11 +51,18 @@ export interface Localizable { } export function initI18n(): void { + // Prevent reinitialization + if (isInitialized) { + return; + } + isInitialized = true; let lang = ''; if (localStorage.getItem('prLang')) lang = localStorage.getItem('prLang'); + + /** * i18next is a localization library for maintaining and using translation resources. * @@ -122,6 +128,9 @@ declare module 'i18next' { pokemonStat: SimpleTranslationEntries; commandUiHandler: SimpleTranslationEntries; fightUiHandler: SimpleTranslationEntries; + titles: SimpleTranslationEntries; + trainerClasses: SimpleTranslationEntries; + trainerNames: SimpleTranslationEntries; tutorial: SimpleTranslationEntries; starterSelectUiHandler: SimpleTranslationEntries; splashMessages: SimpleTranslationEntries; @@ -135,3 +144,9 @@ declare module 'i18next' { } export default i18next; + +export function getIsInitialized(): boolean { + return isInitialized; +} + +let isInitialized = false; \ No newline at end of file From 41a0e90ab07a89d4ff0a0a29756591ce61c2930a Mon Sep 17 00:00:00 2001 From: Lugiad Date: Thu, 16 May 2024 11:06:52 +0200 Subject: [PATCH 40/46] Minor Adjustment to French pokemon-stat.ts (#864) --- src/locales/fr/pokemon-stat.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/locales/fr/pokemon-stat.ts b/src/locales/fr/pokemon-stat.ts index 3ab39f0af23..62aa97fc1fd 100644 --- a/src/locales/fr/pokemon-stat.ts +++ b/src/locales/fr/pokemon-stat.ts @@ -7,10 +7,10 @@ export const pokemonStat: SimpleTranslationEntries = { "ATKshortened": "Atq", "DEF": "Défense", "DEFshortened": "Déf", - "SPATK": "Atq. Spé", + "SPATK": "Atq. Spé.", "SPATKshortened": "AtqSp", - "SPDEF": "Déf. Spé", + "SPDEF": "Déf. Spé.", "SPDEFshortened": "DéfSp", "SPD": "Vitesse", "SPDshortened": "Vit" -} as const; \ No newline at end of file +} as const; From e5cd95859d12592c55597de8355a4493e2d91765 Mon Sep 17 00:00:00 2001 From: mercurius-00 <80205689+mercurius-00@users.noreply.github.com> Date: Thu, 16 May 2024 17:10:11 +0800 Subject: [PATCH 41/46] Chinese localization supplement and fixes (#945) Co-authored-by: hjh --- src/locales/zh_CN/ability-trigger.ts | 2 +- src/locales/zh_CN/battle.ts | 2 +- src/locales/zh_CN/fight-ui-handler.ts | 4 +- src/locales/zh_CN/growth.ts | 12 +- src/locales/zh_CN/menu-ui-handler.ts | 2 +- src/locales/zh_CN/menu.ts | 12 +- src/locales/zh_CN/modifier-type.ts | 538 +++++++++--------- src/locales/zh_CN/nature.ts | 50 +- .../zh_CN/starter-select-ui-handler.ts | 6 +- src/locales/zh_CN/weather.ts | 60 +- 10 files changed, 344 insertions(+), 344 deletions(-) diff --git a/src/locales/zh_CN/ability-trigger.ts b/src/locales/zh_CN/ability-trigger.ts index 88900741218..85152b1bccc 100644 --- a/src/locales/zh_CN/ability-trigger.ts +++ b/src/locales/zh_CN/ability-trigger.ts @@ -1,5 +1,5 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const abilityTriggers: SimpleTranslationEntries = { - 'blockRecoilDamage' : `{{pokemonName}}'s {{abilityName}}\nprotected it from recoil!`, + 'blockRecoilDamage' : `{{pokemonName}} 的 {{abilityName}}\n抵消了反作用力!`, } as const; \ No newline at end of file diff --git a/src/locales/zh_CN/battle.ts b/src/locales/zh_CN/battle.ts index 16efae75afd..f99e2ddc76a 100644 --- a/src/locales/zh_CN/battle.ts +++ b/src/locales/zh_CN/battle.ts @@ -32,7 +32,7 @@ export const battle: SimpleTranslationEntries = { "learnMoveForgetQuestion": "要忘记哪个技能?", "learnMoveForgetSuccess": "{{pokemonName}} 忘记了\n如何使用 {{moveName}}。", "countdownPoof": "@d{32}1, @d{15}2, @d{15}和@d{15}… @d{15}… @d{15}… @d{15}@s{pb_bounce_1}噗!", - "learnMoveAnd": "和…", + "learnMoveAnd": "然后...", "levelCapUp": "等级上限提升到 {{levelCap}}!", "moveNotImplemented": "{{moveName}} 尚未实装,无法选择。", "moveNoPP": "这个技能的 PP 用完了", diff --git a/src/locales/zh_CN/fight-ui-handler.ts b/src/locales/zh_CN/fight-ui-handler.ts index 7546e9af66a..d86767bd13d 100644 --- a/src/locales/zh_CN/fight-ui-handler.ts +++ b/src/locales/zh_CN/fight-ui-handler.ts @@ -2,6 +2,6 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const fightUiHandler: SimpleTranslationEntries = { "pp": "PP", - "power": "Power", - "accuracy": "Accuracy", + "power": "威力", + "accuracy": "命中率", } as const; \ No newline at end of file diff --git a/src/locales/zh_CN/growth.ts b/src/locales/zh_CN/growth.ts index a0d1cb5eeaa..daeeed63385 100644 --- a/src/locales/zh_CN/growth.ts +++ b/src/locales/zh_CN/growth.ts @@ -1,10 +1,10 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const growth: SimpleTranslationEntries = { - "Erratic": "Erratic", - "Fast": "Fast", - "Medium_Fast": "Medium Fast", - "Medium_Slow": "Medium Slow", - "Slow": "Slow", - "Fluctuating": "Fluctuating" + "Erratic": "最快", + "Fast": "快", + "Medium_Fast": "较快", + "Medium_Slow": "较慢", + "Slow": "慢", + "Fluctuating": "最慢" } as const; \ No newline at end of file diff --git a/src/locales/zh_CN/menu-ui-handler.ts b/src/locales/zh_CN/menu-ui-handler.ts index a4d343f6da7..22058daa7cb 100644 --- a/src/locales/zh_CN/menu-ui-handler.ts +++ b/src/locales/zh_CN/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "扭蛋机", "MANAGE_DATA": "管理数据", "COMMUNITY": "社区", - "SAVE_AND_QUIT": "Save and Quit", + "SAVE_AND_QUIT": "保存并退出", "LOG_OUT": "登出", "slot": "存档位 {{slotNumber}}", "importSession": "导入存档", diff --git a/src/locales/zh_CN/menu.ts b/src/locales/zh_CN/menu.ts index 1cbfa905758..14bba6f5e6e 100644 --- a/src/locales/zh_CN/menu.ts +++ b/src/locales/zh_CN/menu.ts @@ -35,15 +35,15 @@ export const menu: SimpleTranslationEntries = { "boyOrGirl": "你是男孩还是女孩?", "boy": "男孩", "girl": "女孩", - "evolving": "What?\n{{pokemonName}} is evolving!", - "stoppedEvolving": "{{pokemonName}} stopped evolving.", - "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", - "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", - "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", + "evolving": "咦?\n{{pokemonName}} 开始进化了!", + "stoppedEvolving": "{{pokemonName}} 停止了进化.", + "pauseEvolutionsQuestion": "你确定要停止 {{pokemonName}} 的进化吗?\n你可以在队伍界面中重新进化.", + "evolutionsPaused": "{{pokemonName}} 的进化停止了.", + "evolutionDone": "恭喜!\n你的 {{pokemonName}} 进化成了 {{evolvedPokemonName}}!", "dailyRankings": "每日排名", "weeklyRankings": "每周排名", "noRankings": "无排名", - "loading": "加载中…", + "loading": "加载中...", "playersOnline": "在线玩家", "empty": "空", "yes": "是", diff --git a/src/locales/zh_CN/modifier-type.ts b/src/locales/zh_CN/modifier-type.ts index 043d7a705d5..80ddc1f92dd 100644 --- a/src/locales/zh_CN/modifier-type.ts +++ b/src/locales/zh_CN/modifier-type.ts @@ -4,406 +4,406 @@ export const modifierType: ModifierTypeTranslationEntries = { ModifierType: { "AddPokeballModifierType": { name: "{{modifierCount}}x {{pokeballName}}", - description: "Receive {{pokeballName}} x{{modifierCount}} (Inventory: {{pokeballAmount}}) \nCatch Rate: {{catchRate}}", + description: "获得 {{pokeballName}} x{{modifierCount}} (已有:{{pokeballAmount}}) \n捕捉倍率:{{catchRate}}", }, "AddVoucherModifierType": { name: "{{modifierCount}}x {{voucherTypeName}}", - description: "Receive {{voucherTypeName}} x{{modifierCount}}", + description: "获得 {{voucherTypeName}} x{{modifierCount}}", }, "PokemonHeldItemModifierType": { extra: { - "inoperable": "{{pokemonName}} can't take\nthis item!", - "tooMany": "{{pokemonName}} has too many\nof this item!", + "inoperable": "{{pokemonName}} 无法携带\n这个物品!", + "tooMany": "{{pokemonName}} 已有太多\n这个物品!", } }, "PokemonHpRestoreModifierType": { - description: "Restores {{restorePoints}} HP or {{restorePercent}}% HP for one Pokémon, whichever is higher", + description: "为一只宝可梦回复 {{restorePoints}} HP 或 {{restorePercent}}% HP,取最大值", extra: { - "fully": "Fully restores HP for one Pokémon", - "fullyWithStatus": "Fully restores HP for one Pokémon and heals any status ailment", + "fully": "为一只宝可梦回复全部HP", + "fullyWithStatus": "为一只宝可梦回复全部HP并消除所有负面状态", } }, "PokemonReviveModifierType": { - description: "Revives one Pokémon and restores {{restorePercent}}% HP", + description: "复活一只宝可梦并回复 {{restorePercent}}% HP", }, "PokemonStatusHealModifierType": { - description: "Heals any status ailment for one Pokémon", + description: "为一只宝可梦消除所有负面状态", }, "PokemonPpRestoreModifierType": { - description: "Restores {{restorePoints}} PP for one Pokémon move", + description: "为一只宝可梦的一个招式回复 {{restorePoints}} PP", extra: { - "fully": "Restores all PP for one Pokémon move", + "fully": "完全回复一只宝可梦一个招式的PP", } }, "PokemonAllMovePpRestoreModifierType": { - description: "Restores {{restorePoints}} PP for all of one Pokémon's moves", + description: "为一只宝可梦的所有招式回复 {{restorePoints}} PP", extra: { - "fully": "Restores all PP for all of one Pokémon's moves", + "fully": "为一只宝可梦的所有招式回复所有PP", } }, "PokemonPpUpModifierType": { - description: "Permanently increases PP for one Pokémon move by {{upPoints}} for every 5 maximum PP (maximum 3)", + description: "为一只宝可梦的一个招式永久增加{{upPoints}}点PP每5点当前最大PP (最多3点)", }, "PokemonNatureChangeModifierType": { - name: "{{natureName}} Mint", - description: "Changes a Pokémon's nature to {{natureName}} and permanently unlocks the nature for the starter.", + name: "{{natureName}}薄荷", + description: "将一只宝可梦的性格改为{{natureName}}并为该宝可梦永久解锁该性格.", }, "DoubleBattleChanceBoosterModifierType": { - description: "Doubles the chance of an encounter being a double battle for {{battleCount}} battles", + description: "接下来的{{battleCount}}场战斗是双打的概率翻倍", }, "TempBattleStatBoosterModifierType": { - description: "Increases the {{tempBattleStatName}} of all party members by 1 stage for 5 battles", + description: "为所有成员宝可梦提升一级{{tempBattleStatName}},持续5场战斗", }, "AttackTypeBoosterModifierType": { - description: "Increases the power of a Pokémon's {{moveType}}-type moves by 20%", + description: "一只宝可梦的{{moveType}}系招式威力提升20%", }, "PokemonLevelIncrementModifierType": { - description: "Increases a Pokémon's level by 1", + description: "一只宝可梦等级提升1级", }, "AllPokemonLevelIncrementModifierType": { - description: "Increases all party members' level by 1", + description: "所有成员宝可梦等级提升1级", }, "PokemonBaseStatBoosterModifierType": { - description: "Increases the holder's base {{statName}} by 10%. The higher your IVs, the higher the stack limit.", + description: "增加持有者的{{statName}}10%. 个体值越高堆叠上限越高.", }, "AllPokemonFullHpRestoreModifierType": { - description: "Restores 100% HP for all Pokémon", + description: "所有宝可梦完全回复HP", }, "AllPokemonFullReviveModifierType": { - description: "Revives all fainted Pokémon, fully restoring HP", + description: "复活所有濒死宝可梦,完全回复HP", }, "MoneyRewardModifierType": { - description: "Grants a {{moneyMultiplier}} amount of money (₽{{moneyAmount}})", + description: "获得{{moneyMultiplier}}金钱 (₽{{moneyAmount}})", extra: { - "small": "small", - "moderate": "moderate", - "large": "large", + "small": "少量", + "moderate": "中等", + "large": "大量", }, }, "ExpBoosterModifierType": { - description: "Increases gain of EXP. Points by {{boostPercent}}%", + description: "EXP.获取量增加{{boostPercent}}%", }, "PokemonExpBoosterModifierType": { - description: "Increases the holder's gain of EXP. Points by {{boostPercent}}%", + description: "持有者EXP.获取量增加{{boostPercent}}%", }, "PokemonFriendshipBoosterModifierType": { - description: "Increases friendship gain per victory by 50%", + description: "每场战斗获得的好感度提升50%", }, "PokemonMoveAccuracyBoosterModifierType": { - description: "Increases move accuracy by {{accuracyAmount}} (maximum 100)", + description: "招式命中率增加{{accuracyAmount}} (最大100)", }, "PokemonMultiHitModifierType": { - description: "Attacks hit one additional time at the cost of a 60/75/82.5% power reduction per stack respectively", + description: "攻击造成一次额外伤害,每次堆叠额外伤害分别衰减60/75/82.5%", }, "TmModifierType": { - name: "TM{{moveId}} - {{moveName}}", - description: "Teach {{moveName}} to a Pokémon", + name: "招式学习器 {{moveId}} - {{moveName}}", + description: "教会一只宝可梦{{moveName}}", }, "EvolutionItemModifierType": { - description: "Causes certain Pokémon to evolve", + description: "使某些宝可梦进化", }, "FormChangeItemModifierType": { - description: "Causes certain Pokémon to change form", + description: "使某些宝可梦更改形态", }, "FusePokemonModifierType": { - description: "Combines two Pokémon (transfers Ability, splits base stats and types, shares move pool)", + description: "融合两只宝可梦 (改变特性, 平分基础点数和属性, 共享招式池)", }, "TerastallizeModifierType": { - name: "{{teraType}} Tera Shard", - description: "{{teraType}} Terastallizes the holder for up to 10 battles", + name: "{{teraType}}太晶碎块", + description: "持有者获得{{teraType}}太晶化10场战斗", }, "ContactHeldItemTransferChanceModifierType": { - description: "Upon attacking, there is a {{chancePercent}}% chance the foe's held item will be stolen", + description: "攻击时{{chancePercent}}%概率偷取对手物品", }, "TurnHeldItemTransferModifierType": { - description: "Every turn, the holder acquires one held item from the foe", + description: "持有者每回合从对手那里获得一个持有的物品", }, "EnemyAttackStatusEffectChanceModifierType": { - description: "Adds a {{chancePercent}}% chance to inflict {{statusEffect}} with attack moves", + description: "攻击时{{chancePercent}}%概率造成{{statusEffect}}", }, "EnemyEndureChanceModifierType": { - description: "Adds a {{chancePercent}}% chance of enduring a hit", + description: "增加{{chancePercent}}%遭受攻击的概率", }, - "RARE_CANDY": { name: "Rare Candy" }, - "RARER_CANDY": { name: "Rarer Candy" }, + "RARE_CANDY": { name: "神奇糖果" }, + "RARER_CANDY": { name: "超神奇糖果" }, - "MEGA_BRACELET": { name: "Mega Bracelet", description: "Mega Stones become available" }, - "DYNAMAX_BAND": { name: "Dynamax Band", description: "Max Mushrooms become available" }, - "TERA_ORB": { name: "Tera Orb", description: "Tera Shards become available" }, + "MEGA_BRACELET": { name: "超级手镯", description: "能让携带着超级石战斗的宝可梦进行超级进化" }, + "DYNAMAX_BAND": { name: "极巨腕带", description: "能让携带着极巨菇菇战斗的宝可梦进行极巨化" }, + "TERA_ORB": { name: "太晶珠", description: "能让携带着太晶碎块战斗的宝可梦进行太晶化" }, - "MAP": { name: "Map", description: "Allows you to choose your destination at a crossroads" }, + "MAP": { name: "地图", description: "允许你在切换宝可梦群落时选择目的地"}, - "POTION": { name: "Potion" }, - "SUPER_POTION": { name: "Super Potion" }, - "HYPER_POTION": { name: "Hyper Potion" }, - "MAX_POTION": { name: "Max Potion" }, - "FULL_RESTORE": { name: "Full Restore" }, + "POTION": { name: "伤药" }, + "SUPER_POTION": { name: "好伤药" }, + "HYPER_POTION": { name: "厉害伤药" }, + "MAX_POTION": { name: "全满药" }, + "FULL_RESTORE": { name: "全复药" }, - "REVIVE": { name: "Revive" }, - "MAX_REVIVE": { name: "Max Revive" }, + "REVIVE": { name: "活力碎片" }, + "MAX_REVIVE": { name: "活力块" }, - "FULL_HEAL": { name: "Full Heal" }, + "FULL_HEAL": { name: "万灵药" }, - "SACRED_ASH": { name: "Sacred Ash" }, + "SACRED_ASH": { name: "圣灰" }, - "REVIVER_SEED": { name: "Reviver Seed", description: "Revives the holder for 1/2 HP upon fainting" }, + "REVIVER_SEED": { name: "复活种子", description: "恢复1只濒死宝可梦的HP至1/2" }, - "ETHER": { name: "Ether" }, - "MAX_ETHER": { name: "Max Ether" }, + "ETHER": { name: "PP单项小补剂" }, + "MAX_ETHER": { name: "PP单项全补剂" }, - "ELIXIR": { name: "Elixir" }, - "MAX_ELIXIR": { name: "Max Elixir" }, + "ELIXIR": { name: "PP多项小补剂" }, + "MAX_ELIXIR": { name: "PP多项全补剂" }, - "PP_UP": { name: "PP Up" }, - "PP_MAX": { name: "PP Max" }, + "PP_UP": { name: "PP提升剂" }, + "PP_MAX": { name: "PP极限提升剂" }, - "LURE": { name: "Lure" }, - "SUPER_LURE": { name: "Super Lure" }, - "MAX_LURE": { name: "Max Lure" }, + "LURE": { name: "引虫香水" }, + "SUPER_LURE": { name: "白银香水" }, + "MAX_LURE": { name: "黄金香水" }, - "MEMORY_MUSHROOM": { name: "Memory Mushroom", description: "Recall one Pokémon's forgotten move" }, + "MEMORY_MUSHROOM": { name: "回忆蘑菇", description: "回忆一个宝可梦已经遗忘的招式" }, - "EXP_SHARE": { name: "EXP. All", description: "Non-participants receive 20% of a single participant's EXP. Points" }, - "EXP_BALANCE": { name: "EXP. Balance", description: "Weighs EXP. Points received from battles towards lower-leveled party members" }, + "EXP_SHARE": { name: "学习装置", description: "未参加对战的宝可梦获得20%的经验值" }, + "EXP_BALANCE": { name: "均衡型学习装置", description: "增加战斗中获得的EXP.分配给低级成员宝可梦的权重" }, - "OVAL_CHARM": { name: "Oval Charm", description: "When multiple Pokémon participate in a battle, each gets an extra 10% of the total EXP" }, + "OVAL_CHARM": { name: "圆形护符", description: "当多只宝可梦参与战斗, 分别获得总EXP.10%的额外EXP." }, - "EXP_CHARM": { name: "EXP. Charm" }, - "SUPER_EXP_CHARM": { name: "Super EXP. Charm" }, - "GOLDEN_EXP_CHARM": { name: "Golden EXP. Charm" }, + "EXP_CHARM": { name: "经验护符" }, + "SUPER_EXP_CHARM": { name: "超级经验护符" }, + "GOLDEN_EXP_CHARM": { name: "黄金经验护符" }, - "LUCKY_EGG": { name: "Lucky Egg" }, - "GOLDEN_EGG": { name: "Golden Egg" }, + "LUCKY_EGG": { name: "幸运蛋" }, + "GOLDEN_EGG": { name: "金蛋" }, - "SOOTHE_BELL": { name: "Soothe Bell" }, + "SOOTHE_BELL": { name: "安抚之铃" }, - "SOUL_DEW": { name: "Soul Dew", description: "Increases the influence of a Pokémon's nature on its stats by 10% (additive)" }, + "SOUL_DEW": { name: "心之水滴", description: "增加宝可梦性格影响10% (加算)" }, - "NUGGET": { name: "Nugget" }, - "BIG_NUGGET": { name: "Big Nugget" }, - "RELIC_GOLD": { name: "Relic Gold" }, + "NUGGET": { name: "金珠" }, + "BIG_NUGGET": { name: "巨大金珠" }, + "RELIC_GOLD": { name: "古代金币" }, - "AMULET_COIN": { name: "Amulet Coin", description: "Increases money rewards by 20%" }, - "GOLDEN_PUNCH": { name: "Golden Punch", description: "Grants 50% of damage inflicted as money" }, - "COIN_CASE": { name: "Coin Case", description: "After every 10th battle, receive 10% of your money in interest" }, + "AMULET_COIN": { name: "护符金币", description: "金钱奖励增加20%" }, + "GOLDEN_PUNCH": { name: "黄金拳头", description: "将50%造成的伤害转换为金钱" }, + "COIN_CASE": { name: "代币盒", description: "每十场战斗, 获得自己金钱10%的利息" }, - "LOCK_CAPSULE": { name: "Lock Capsule", description: "Allows you to lock item rarities when rerolling items" }, + "LOCK_CAPSULE": { name: "上锁的容器", description: "允许在刷新物品时锁定物品稀有度" }, - "GRIP_CLAW": { name: "Grip Claw" }, - "WIDE_LENS": { name: "Wide Lens" }, + "GRIP_CLAW": { name: "紧缠钩爪" }, + "WIDE_LENS": { name: "广角镜" }, - "MULTI_LENS": { name: "Multi Lens" }, + "MULTI_LENS": { name: "多重镜" }, - "HEALING_CHARM": { name: "Healing Charm", description: "Increases the effectiveness of HP restoring moves and items by 10% (excludes Revives)" }, - "CANDY_JAR": { name: "Candy Jar", description: "Increases the number of levels added by Rare Candy items by 1" }, + "HEALING_CHARM": { name: "治愈护符", description: "HP回复量增加10% (含复活)" }, + "CANDY_JAR": { name: "糖果罐", description: "神奇糖果提供的升级提升1级" }, - "BERRY_POUCH": { name: "Berry Pouch", description: "Adds a 25% chance that a used berry will not be consumed" }, + "BERRY_POUCH": { name: "树果袋", description: "使用树果时有25%的几率不会消耗树果" }, - "FOCUS_BAND": { name: "Focus Band", description: "Adds a 10% chance to survive with 1 HP after being damaged enough to faint" }, + "FOCUS_BAND": { name: "气势头带", description: "携带该道具的宝可梦有10%几率在受到攻击而将陷入濒死状态时,保留1点HP不陷入濒死状态。" }, - "QUICK_CLAW": { name: "Quick Claw", description: "Adds a 10% chance to move first regardless of speed (after priority)" }, + "QUICK_CLAW": { name: "先制之爪", description: "有10%的几率无视速度优先使出招式 (先制技能优先)" }, - "KINGS_ROCK": { name: "King's Rock", description: "Adds a 10% chance an attack move will cause the opponent to flinch" }, + "KINGS_ROCK": { name: "王者之证", description: "携带该道具的宝可梦使用任意原本不会造成畏缩状态的攻击招式并造成伤害时,有10%几率使目标陷入畏缩状态。" }, - "LEFTOVERS": { name: "Leftovers", description: "Heals 1/16 of a Pokémon's maximum HP every turn" }, - "SHELL_BELL": { name: "Shell Bell", description: "Heals 1/8 of a Pokémon's dealt damage" }, + "LEFTOVERS": { name: "吃剩的东西", description: "携带该道具的宝可梦在每个回合结束时恢复最大HP的1/16" }, + "SHELL_BELL": { name: "贝壳之铃", description: "携带该道具的宝可梦在攻击对方成功造成伤害时,携带者的HP会恢复其所造成伤害的1/8" }, - "BATON": { name: "Baton", description: "Allows passing along effects when switching Pokémon, which also bypasses traps" }, + "BATON": { name: "接力棒", description: "允许在切换宝可梦时保留能力变化, 对陷阱同样生效" }, - "SHINY_CHARM": { name: "Shiny Charm", description: "Dramatically increases the chance of a wild Pokémon being Shiny" }, - "ABILITY_CHARM": { name: "Ability Charm", description: "Dramatically increases the chance of a wild Pokémon having a Hidden Ability" }, + "SHINY_CHARM": { name: "闪耀护符", description: "显著增加野生宝可梦的闪光概率" }, + "ABILITY_CHARM": { name: "特性护符", description: "显著增加野生宝可梦有隐藏特性的概率" }, - "IV_SCANNER": { name: "IV Scanner", description: "Allows scanning the IVs of wild Pokémon. 2 IVs are revealed per stack. The best IVs are shown first" }, + "IV_SCANNER": { name: "个体值探测器", description: "允许扫描野生宝可梦的个体值。 每个次显示2个个体值. 最好的个体值优先显示" }, - "DNA_SPLICERS": { name: "DNA Splicers" }, + "DNA_SPLICERS": { name: "基因之楔" }, - "MINI_BLACK_HOLE": { name: "Mini Black Hole" }, + "MINI_BLACK_HOLE": { name: "迷你黑洞" }, - "GOLDEN_POKEBALL": { name: "Golden Poké Ball", description: "Adds 1 extra item option at the end of every battle" }, + "GOLDEN_POKEBALL": { name: "黄金精灵球", description: "在每场战斗结束后增加一个额外物品选项" }, - "ENEMY_DAMAGE_BOOSTER": { name: "Damage Token", description: "Increases damage by 5%" }, - "ENEMY_DAMAGE_REDUCTION": { name: "Protection Token", description: "Reduces incoming damage by 2.5%" }, - "ENEMY_HEAL": { name: "Recovery Token", description: "Heals 2% of max HP every turn" }, - "ENEMY_ATTACK_POISON_CHANCE": { name: "Poison Token" }, - "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "Paralyze Token" }, - "ENEMY_ATTACK_SLEEP_CHANCE": { name: "Sleep Token" }, - "ENEMY_ATTACK_FREEZE_CHANCE": { name: "Freeze Token" }, - "ENEMY_ATTACK_BURN_CHANCE": { name: "Burn Token" }, - "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "Full Heal Token", description: "Adds a 10% chance every turn to heal a status condition" }, - "ENEMY_ENDURE_CHANCE": { name: "Endure Token" }, - "ENEMY_FUSED_CHANCE": { name: "Fusion Token", description: "Adds a 1% chance that a wild Pokémon will be a fusion" }, + "ENEMY_DAMAGE_BOOSTER": { name: "伤害硬币", description: "增加5%造成伤害" }, + "ENEMY_DAMAGE_REDUCTION": { name: "防御硬币", description: "减少2.5%承受伤害" }, + "ENEMY_HEAL": { name: "回复硬币", description: "每回合回复2%最大HP" }, + "ENEMY_ATTACK_POISON_CHANCE": { name: "剧毒硬币" }, + "ENEMY_ATTACK_PARALYZE_CHANCE": { name: "麻痹硬币" }, + "ENEMY_ATTACK_SLEEP_CHANCE": { name: "睡眠硬币" }, + "ENEMY_ATTACK_FREEZE_CHANCE": { name: "冰冻硬币" }, + "ENEMY_ATTACK_BURN_CHANCE": { name: "灼烧硬币" }, + "ENEMY_STATUS_EFFECT_HEAL_CHANCE": { name: "万灵药硬币", description: "增加10%每回合治愈异常状态的概率" }, + "ENEMY_ENDURE_CHANCE": { name: "忍受硬币" }, + "ENEMY_FUSED_CHANCE": { name: "融合硬币", description: "增加1%野生融合宝可梦出现概率" }, }, TempBattleStatBoosterItem: { - "x_attack": "X Attack", - "x_defense": "X Defense", - "x_sp_atk": "X Sp. Atk", - "x_sp_def": "X Sp. Def", - "x_speed": "X Speed", - "x_accuracy": "X Accuracy", - "dire_hit": "Dire Hit", + "x_attack": "力量强化", + "x_defense": "防御强化", + "x_sp_atk": "特攻强化", + "x_sp_def": "特防强化", + "x_speed": "速度强化", + "x_accuracy": "命中强化", + "dire_hit": "要害攻击", }, AttackTypeBoosterItem: { - "silk_scarf": "Silk Scarf", - "black_belt": "Black Belt", - "sharp_beak": "Sharp Beak", - "poison_barb": "Poison Barb", - "soft_sand": "Soft Sand", - "hard_stone": "Hard Stone", - "silver_powder": "Silver Powder", - "spell_tag": "Spell Tag", - "metal_coat": "Metal Coat", - "charcoal": "Charcoal", - "mystic_water": "Mystic Water", - "miracle_seed": "Miracle Seed", - "magnet": "Magnet", - "twisted_spoon": "Twisted Spoon", - "never_melt_ice": "Never-Melt Ice", - "dragon_fang": "Dragon Fang", - "black_glasses": "Black Glasses", - "fairy_feather": "Fairy Feather", + "silk_scarf": "丝绸围巾", + "black_belt": "黑带", + "sharp_beak": "锐利鸟嘴", + "poison_barb": "毒针", + "soft_sand": "柔软沙子", + "hard_stone": "硬石头", + "silver_powder": "银粉", + "spell_tag": "诅咒之符", + "metal_coat": "金属膜", + "charcoal": "木炭", + "mystic_water": "神秘水滴", + "miracle_seed": "奇迹种子", + "magnet": "磁铁", + "twisted_spoon": "弯曲的汤匙", + "never_melt_ice": "不融冰", + "dragon_fang": "龙之牙", + "black_glasses": "黑色眼镜", + "fairy_feather": "妖精之羽", }, BaseStatBoosterItem: { - "hp_up": "HP Up", - "protein": "Protein", - "iron": "Iron", - "calcium": "Calcium", - "zinc": "Zinc", - "carbos": "Carbos", + "hp_up": "HP增强剂", + "protein": "攻击增强剂", + "iron": "防御增强剂", + "calcium": "特攻增强剂", + "zinc": "特防增强剂", + "carbos": "速度增强剂", }, EvolutionItem: { "NONE": "None", - "LINKING_CORD": "Linking Cord", - "SUN_STONE": "Sun Stone", - "MOON_STONE": "Moon Stone", - "LEAF_STONE": "Leaf Stone", - "FIRE_STONE": "Fire Stone", - "WATER_STONE": "Water Stone", - "THUNDER_STONE": "Thunder Stone", - "ICE_STONE": "Ice Stone", - "DUSK_STONE": "Dusk Stone", - "DAWN_STONE": "Dawn Stone", - "SHINY_STONE": "Shiny Stone", - "CRACKED_POT": "Cracked Pot", - "SWEET_APPLE": "Sweet Apple", - "TART_APPLE": "Tart Apple", - "STRAWBERRY_SWEET": "Strawberry Sweet", - "UNREMARKABLE_TEACUP": "Unremarkable Teacup", + "LINKING_CORD": "联系绳", + "SUN_STONE": "日之石", + "MOON_STONE": "月之石", + "LEAF_STONE": "叶之石", + "FIRE_STONE": "火之石", + "WATER_STONE": "水之石", + "THUNDER_STONE": "雷之石", + "ICE_STONE": "冰之石", + "DUSK_STONE": "暗之石", + "DAWN_STONE": "觉醒之石", + "SHINY_STONE": "光之石", + "CRACKED_POT": "破裂的茶壶", + "SWEET_APPLE": "甜甜苹果", + "TART_APPLE": "酸酸苹果", + "STRAWBERRY_SWEET": "草莓糖饰", + "UNREMARKABLE_TEACUP": "凡作茶碗", - "CHIPPED_POT": "Chipped Pot", - "BLACK_AUGURITE": "Black Augurite", - "GALARICA_CUFF": "Galarica Cuff", - "GALARICA_WREATH": "Galarica Wreath", - "PEAT_BLOCK": "Peat Block", - "AUSPICIOUS_ARMOR": "Auspicious Armor", - "MALICIOUS_ARMOR": "Malicious Armor", - "MASTERPIECE_TEACUP": "Masterpiece Teacup", - "METAL_ALLOY": "Metal Alloy", - "SCROLL_OF_DARKNESS": "Scroll Of Darkness", - "SCROLL_OF_WATERS": "Scroll Of Waters", - "SYRUPY_APPLE": "Syrupy Apple", + "CHIPPED_POT": "缺损的茶壶", + "BLACK_AUGURITE": "黑奇石", + "GALARICA_CUFF": "伽勒豆蔻手环", + "GALARICA_WREATH": "伽勒豆蔻花圈", + "PEAT_BLOCK": "泥炭块", + "AUSPICIOUS_ARMOR": "庆祝之铠", + "MALICIOUS_ARMOR": "咒术之铠", + "MASTERPIECE_TEACUP": "杰作茶碗", + "METAL_ALLOY": "复合金属", + "SCROLL_OF_DARKNESS": "恶之挂轴", + "SCROLL_OF_WATERS": "水之挂轴", + "SYRUPY_APPLE": "蜜汁苹果", }, FormChangeItem: { "NONE": "None", - "ABOMASITE": "Abomasite", - "ABSOLITE": "Absolite", - "AERODACTYLITE": "Aerodactylite", - "AGGRONITE": "Aggronite", - "ALAKAZITE": "Alakazite", - "ALTARIANITE": "Altarianite", - "AMPHAROSITE": "Ampharosite", - "AUDINITE": "Audinite", - "BANETTITE": "Banettite", - "BEEDRILLITE": "Beedrillite", - "BLASTOISINITE": "Blastoisinite", - "BLAZIKENITE": "Blazikenite", - "CAMERUPTITE": "Cameruptite", - "CHARIZARDITE_X": "Charizardite X", - "CHARIZARDITE_Y": "Charizardite Y", - "DIANCITE": "Diancite", - "GALLADITE": "Galladite", - "GARCHOMPITE": "Garchompite", - "GARDEVOIRITE": "Gardevoirite", - "GENGARITE": "Gengarite", - "GLALITITE": "Glalitite", - "GYARADOSITE": "Gyaradosite", - "HERACRONITE": "Heracronite", - "HOUNDOOMINITE": "Houndoominite", - "KANGASKHANITE": "Kangaskhanite", - "LATIASITE": "Latiasite", - "LATIOSITE": "Latiosite", - "LOPUNNITE": "Lopunnite", - "LUCARIONITE": "Lucarionite", - "MANECTITE": "Manectite", - "MAWILITE": "Mawilite", - "MEDICHAMITE": "Medichamite", - "METAGROSSITE": "Metagrossite", - "MEWTWONITE_X": "Mewtwonite X", - "MEWTWONITE_Y": "Mewtwonite Y", - "PIDGEOTITE": "Pidgeotite", - "PINSIRITE": "Pinsirite", - "RAYQUAZITE": "Rayquazite", - "SABLENITE": "Sablenite", - "SALAMENCITE": "Salamencite", - "SCEPTILITE": "Sceptilite", - "SCIZORITE": "Scizorite", - "SHARPEDONITE": "Sharpedonite", - "SLOWBRONITE": "Slowbronite", - "STEELIXITE": "Steelixite", - "SWAMPERTITE": "Swampertite", - "TYRANITARITE": "Tyranitarite", - "VENUSAURITE": "Venusaurite", + "ABOMASITE": "暴雪王进化石", + "ABSOLITE": "阿勃梭鲁进化石", + "AERODACTYLITE": "化石翼龙进化石", + "AGGRONITE": "波士可多拉进化石", + "ALAKAZITE": "胡地进化石", + "ALTARIANITE": "七夕青鸟进化石", + "AMPHAROSITE": "电龙进化石", + "AUDINITE": "差不多娃娃进化石", + "BANETTITE": "诅咒娃娃进化石", + "BEEDRILLITE": "大针蜂进化石", + "BLASTOISINITE": "水箭龟进化石", + "BLAZIKENITE": "火焰鸡进化石", + "CAMERUPTITE": "喷火驼进化石", + "CHARIZARDITE_X": "喷火龙进化石X", + "CHARIZARDITE_Y": "喷火龙进化石Y", + "DIANCITE": "蒂安希进化石", + "GALLADITE": "艾路雷朵进化石", + "GARCHOMPITE": "烈咬陆鲨进化石", + "GARDEVOIRITE": "沙奈朵进化石", + "GENGARITE": "耿鬼进化石", + "GLALITITE": "冰鬼护进化石", + "GYARADOSITE": "暴鲤龙进化石", + "HERACRONITE": "赫拉克罗斯进化石", + "HOUNDOOMINITE": "黑鲁加进化石", + "KANGASKHANITE": "袋兽进化石", + "LATIASITE": "拉帝亚斯进化石", + "LATIOSITE": "拉帝欧斯进化石", + "LOPUNNITE": "长耳兔进化石", + "LUCARIONITE": "路卡利欧进化石", + "MANECTITE": "雷电兽进化石", + "MAWILITE": "大嘴娃进化石", + "MEDICHAMITE": "恰雷姆进化石", + "METAGROSSITE": "巨金怪进化石", + "MEWTWONITE_X": "超梦进化石X", + "MEWTWONITE_Y": "超梦进化石Y", + "PIDGEOTITE": "大比鸟进化石", + "PINSIRITE": "凯罗斯进化石", + "RAYQUAZITE": "烈空坐进化石", + "SABLENITE": "勾魂眼进化石", + "SALAMENCITE": "暴飞龙进化石", + "SCEPTILITE": "蜥蜴王进化石", + "SCIZORITE": "巨钳螳螂进化石", + "SHARPEDONITE": "巨牙鲨进化石", + "SLOWBRONITE": "呆壳兽进化石", + "STEELIXITE": "大钢蛇进化石", + "SWAMPERTITE": "巨沼怪进化石", + "TYRANITARITE": "班基拉斯进化石", + "VENUSAURITE": "妙蛙花进化石", - "BLUE_ORB": "Blue Orb", - "RED_ORB": "Red Orb", - "SHARP_METEORITE": "Sharp Meteorite", - "HARD_METEORITE": "Hard Meteorite", - "SMOOTH_METEORITE": "Smooth Meteorite", - "ADAMANT_CRYSTAL": "Adamant Crystal", - "LUSTROUS_ORB": "Lustrous Orb", - "GRISEOUS_CORE": "Griseous Core", - "REVEAL_GLASS": "Reveal Glass", - "GRACIDEA": "Gracidea", - "MAX_MUSHROOMS": "Max Mushrooms", - "DARK_STONE": "Dark Stone", - "LIGHT_STONE": "Light Stone", - "PRISON_BOTTLE": "Prison Bottle", - "N_LUNARIZER": "N Lunarizer", - "N_SOLARIZER": "N Solarizer", - "RUSTED_SWORD": "Rusted Sword", - "RUSTED_SHIELD": "Rusted Shield", - "ICY_REINS_OF_UNITY": "Icy Reins Of Unity", - "SHADOW_REINS_OF_UNITY": "Shadow Reins Of Unity", - "WELLSPRING_MASK": "Wellspring Mask", - "HEARTHFLAME_MASK": "Hearthflame Mask", - "CORNERSTONE_MASK": "Cornerstone Mask", - "SHOCK_DRIVE": "Shock Drive", - "BURN_DRIVE": "Burn Drive", - "CHILL_DRIVE": "Chill Drive", - "DOUSE_DRIVE": "Douse Drive", + "BLUE_ORB": "靛蓝色宝珠", + "RED_ORB": "朱红色宝珠", + "SHARP_METEORITE": "锐利陨石", + "HARD_METEORITE": "坚硬陨石", + "SMOOTH_METEORITE": "光滑陨石", + "ADAMANT_CRYSTAL": "大金刚宝玉", + "LUSTROUS_ORB": "白玉宝珠", + "GRISEOUS_CORE": "大白金宝玉", + "REVEAL_GLASS": "现形镜", + "GRACIDEA": "葛拉西蒂亚花", + "MAX_MUSHROOMS": "极巨菇菇", + "DARK_STONE": "黑暗石", + "LIGHT_STONE": "光明石", + "PRISON_BOTTLE": "惩戒之壶", + "N_LUNARIZER": "奈克洛露奈合体器", + "N_SOLARIZER": "奈克洛索尔合体器", + "RUSTED_SWORD": "腐朽的剑", + "RUSTED_SHIELD": "腐朽的盾", + "ICY_REINS_OF_UNITY": "牵绊缰绳(冰)", + "SHADOW_REINS_OF_UNITY": "牵绊缰绳(幽灵)", + "WELLSPRING_MASK": "水井面具", + "HEARTHFLAME_MASK": "火灶面具", + "CORNERSTONE_MASK": "础石面具", + "SHOCK_DRIVE": "闪电卡带", + "BURN_DRIVE": "火焰卡带", + "CHILL_DRIVE": "冰冻卡带", + "DOUSE_DRIVE": "水流卡带", }, TeraType: { "UNKNOWN": "Unknown", - "NORMAL": "Normal", - "FIGHTING": "Fighting", - "FLYING": "Flying", - "POISON": "Poison", - "GROUND": "Ground", - "ROCK": "Rock", - "BUG": "Bug", - "GHOST": "Ghost", - "STEEL": "Steel", - "FIRE": "Fire", - "WATER": "Water", - "GRASS": "Grass", - "ELECTRIC": "Electric", - "PSYCHIC": "Psychic", - "ICE": "Ice", - "DRAGON": "Dragon", - "DARK": "Dark", - "FAIRY": "Fairy", - "STELLAR": "Stellar", + "NORMAL": "一般", + "FIGHTING": "格斗", + "FLYING": "飞行", + "POISON": "毒", + "GROUND": "地面", + "ROCK": "岩石", + "BUG": "虫", + "GHOST": "幽灵", + "STEEL": "钢", + "FIRE": "火", + "WATER": "水", + "GRASS": "草", + "ELECTRIC": "电", + "PSYCHIC": "超能力", + "ICE": "冰", + "DRAGON": "龙", + "DARK": "恶", + "FAIRY": "妖精", + "STELLAR": "星晶", }, } as const; \ No newline at end of file diff --git a/src/locales/zh_CN/nature.ts b/src/locales/zh_CN/nature.ts index f29917ff60d..00beeefdfa4 100644 --- a/src/locales/zh_CN/nature.ts +++ b/src/locales/zh_CN/nature.ts @@ -1,29 +1,29 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const nature: SimpleTranslationEntries = { - "Hardy": "Hardy", - "Lonely": "Lonely", - "Brave": "Brave", - "Adamant": "Adamant", - "Naughty": "Naughty", - "Bold": "Bold", - "Docile": "Docile", - "Relaxed": "Relaxed", - "Impish": "Impish", - "Lax": "Lax", - "Timid": "Timid", - "Hasty": "Hasty", - "Serious": "Serious", - "Jolly": "Jolly", - "Naive": "Naive", - "Modest": "Modest", - "Mild": "Mild", - "Quiet": "Quiet", - "Bashful": "Bashful", - "Rash": "Rash", - "Calm": "Calm", - "Gentle": "Gentle", - "Sassy": "Sassy", - "Careful": "Careful", - "Quirky": "Quirky" + "Hardy": "勤奋", + "Lonely": "怕寂寞", + "Brave": "勇敢", + "Adamant": "固执", + "Naughty": "顽皮", + "Bold": "大胆", + "Docile": "坦率", + "Relaxed": "悠闲", + "Impish": "淘气", + "Lax": "乐天", + "Timid": "胆小", + "Hasty": "急躁", + "Serious": "认真", + "Jolly": "爽朗", + "Naive": "天真", + "Modest": "内敛", + "Mild": "慢吞吞", + "Quiet": "冷静", + "Bashful": "害羞", + "Rash": "马虎", + "Calm": "温和", + "Gentle": "温顺", + "Sassy": "自大", + "Careful": "慎重", + "Quirky": "浮躁" } as const; \ No newline at end of file diff --git a/src/locales/zh_CN/starter-select-ui-handler.ts b/src/locales/zh_CN/starter-select-ui-handler.ts index 99ecc31afbb..0713b454376 100644 --- a/src/locales/zh_CN/starter-select-ui-handler.ts +++ b/src/locales/zh_CN/starter-select-ui-handler.ts @@ -38,7 +38,7 @@ export const starterSelectUiHandler: SimpleTranslationEntries = { "cycleVariant": 'V: 切换变种', "enablePassive": "启用被动", "disablePassive": "禁用被动", - "locked": "Locked", - "disabled": "Disabled", - "uncaught": "Uncaught" + "locked": "未解锁", + "disabled": "已禁用", + "uncaught": "未捕获" } diff --git a/src/locales/zh_CN/weather.ts b/src/locales/zh_CN/weather.ts index 999613f1566..50fb2227b2b 100644 --- a/src/locales/zh_CN/weather.ts +++ b/src/locales/zh_CN/weather.ts @@ -4,41 +4,41 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; * The weather namespace holds text displayed when weather is active during a battle */ export const weather: SimpleTranslationEntries = { - "sunnyStartMessage": "The sunlight got bright!", - "sunnyLapseMessage": "The sunlight is strong.", - "sunnyClearMessage": "The sunlight faded.", + "sunnyStartMessage": "日照变强了!", + "sunnyLapseMessage": "日照很强。", + "sunnyClearMessage": "日照复原了。", - "rainStartMessage": "A downpour started!", - "rainLapseMessage": "The downpour continues.", - "rainClearMessage": "The rain stopped.", + "rainStartMessage": "下大雨了!", + "rainLapseMessage": "雨继续下。", + "rainClearMessage": "雨停了。", - "sandstormStartMessage": "A sandstorm brewed!", - "sandstormLapseMessage": "The sandstorm rages.", - "sandstormClearMessage": "The sandstorm subsided.", - "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + "sandstormStartMessage": "开始刮沙尘暴了!", + "sandstormLapseMessage": "沙尘暴肆虐。", + "sandstormClearMessage": "沙尘暴停止了。", + "sandstormDamageMessage": "沙尘暴袭击了{{pokemonPrefix}}{{pokemonName}}!", - "hailStartMessage": "It started to hail!", - "hailLapseMessage": "Hail continues to fall.", - "hailClearMessage": "The hail stopped.", - "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + "hailStartMessage": "开始下冰雹了!", + "hailLapseMessage": "冰雹继续肆虐。", + "hailClearMessage": "冰雹不再下了。", + "hailDamageMessage": "冰雹袭击了{{pokemonPrefix}}{{pokemonName}}!", - "snowStartMessage": "It started to snow!", - "snowLapseMessage": "The snow is falling down.", - "snowClearMessage": "The snow stopped.", + "snowStartMessage": "开始下雪了!", + "snowLapseMessage": "雪继续下。", + "snowClearMessage": "雪停了。", - "fogStartMessage": "A thick fog emerged!", - "fogLapseMessage": "The fog continues.", - "fogClearMessage": "The fog disappeared.", + "fogStartMessage": "起雾了!", + "fogLapseMessage": "雾很浓。", + "fogClearMessage": "雾散了。", - "heavyRainStartMessage": "A heavy downpour started!", - "heavyRainLapseMessage": "The heavy downpour continues.", - "heavyRainClearMessage": "The heavy rain stopped.", - - "harshSunStartMessage": "The sunlight got hot!", - "harshSunLapseMessage": "The sun is scorching hot.", - "harshSunClearMessage": "The harsh sunlight faded.", + "heavyRainStartMessage": "开始下起了暴雨!", + "heavyRainLapseMessage": "暴雨势头不减。", + "heavyRainClearMessage": "暴雨停了。", - "strongWindsStartMessage": "A heavy wind began!", - "strongWindsLapseMessage": "The wind blows intensely.", - "strongWindsClearMessage": "The heavy wind stopped." + "harshSunStartMessage": "日照变得非常强了!", + "harshSunLapseMessage": "强日照势头不减。", + "harshSunClearMessage": "日照复原了。", + + "strongWindsStartMessage": "吹起了神秘的乱流!", + "strongWindsLapseMessage": "神秘的乱流势头不减。", + "strongWindsClearMessage": "神秘的乱流停止了。" } \ No newline at end of file From 36d0243122c2d4f74c02fa9244c94d2fbf13a98a Mon Sep 17 00:00:00 2001 From: Gerafique <155723753+Gerafique@users.noreply.github.com> Date: Thu, 16 May 2024 11:12:58 +0200 Subject: [PATCH 42/46] Update translations menu-ui-handler.ts (#946) changed logout added Save_and_quit message --- src/locales/de/menu-ui-handler.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/locales/de/menu-ui-handler.ts b/src/locales/de/menu-ui-handler.ts index 0197598cb81..aa09a3b4c6f 100644 --- a/src/locales/de/menu-ui-handler.ts +++ b/src/locales/de/menu-ui-handler.ts @@ -9,8 +9,8 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Eier-Gacha", "MANAGE_DATA": "Daten verwalten", "COMMUNITY": "Community", - "SAVE_AND_QUIT": "Save and Quit", - "LOG_OUT": "Ausloggen", + "SAVE_AND_QUIT": "Speichern und Beenden", + "LOG_OUT": "Abmelden", "slot": "Slot {{slotNumber}}", "importSession": "Sitzung importieren", "importSlotSelect": "Wähle einen Slot zum Importieren.", @@ -20,4 +20,4 @@ export const menuUiHandler: SimpleTranslationEntries = { "exportData": "Daten exportieren", "cancel": "Abbrechen", "losingProgressionWarning": "Du wirst jeglichen Fortschritt seit Anfang dieses Kampfes verlieren. Fortfahren?" -} as const; \ No newline at end of file +} as const; From 88fab1dc5f44c7fcf5fdd34aae8553d789b5e81c Mon Sep 17 00:00:00 2001 From: Alessandro Bruzzese <69127023+Bruzzii@users.noreply.github.com> Date: Thu, 16 May 2024 11:13:27 +0200 Subject: [PATCH 43/46] Update italian menu (#954) --- src/locales/it/menu-ui-handler.ts | 2 +- src/locales/it/menu.ts | 10 +++++----- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/locales/it/menu-ui-handler.ts b/src/locales/it/menu-ui-handler.ts index 3e4362e76cf..e0328fccdc1 100644 --- a/src/locales/it/menu-ui-handler.ts +++ b/src/locales/it/menu-ui-handler.ts @@ -9,7 +9,7 @@ export const menuUiHandler: SimpleTranslationEntries = { "EGG_GACHA": "Gacha Uova", "MANAGE_DATA": "Gestisci Dati", "COMMUNITY": "Community", - "SAVE_AND_QUIT": "Save and Quit", + "SAVE_AND_QUIT": "Salva ed Esci", "LOG_OUT": "Disconnettiti", "slot": "Slot {{slotNumber}}", "importSession": "Importa Sessione", diff --git a/src/locales/it/menu.ts b/src/locales/it/menu.ts index ff41b8ab9dc..e86a6be25ed 100644 --- a/src/locales/it/menu.ts +++ b/src/locales/it/menu.ts @@ -40,11 +40,11 @@ export const menu: SimpleTranslationEntries = { "noRankings": "Nessuna Classifica", "loading": "Caricamento…", "playersOnline": "Giocatori Online", - "evolving": "What?\n{{pokemonName}} is evolving!", - "stoppedEvolving": "{{pokemonName}} stopped evolving.", - "pauseEvolutionsQuestion": "Would you like to pause evolutions for {{pokemonName}}?\nEvolutions can be re-enabled from the party screen.", - "evolutionsPaused": "Evolutions have been paused for {{pokemonName}}.", - "evolutionDone": "Congratulations!\nYour {{pokemonName}} evolved into {{evolvedPokemonName}}!", + "evolving": "Cosa?\n{{pokemonName}} si evolvendo!", + "stoppedEvolving": "{{pokemonName}} ha smesso di evolversi.", + "pauseEvolutionsQuestion": "Vuoi sospendere le evoluzioni per {{pokemonName}}?\nLe evoluzioni possono essere riattivate dalla schermata del party.", + "evolutionsPaused": "Le evoluzioni sono state sospese per {{pokemonName}}.", + "evolutionDone": "Congratulazioni!\n{{pokemonName}} si è evoluto in {{evolvedPokemonName}}!", "empty":"Vuoto", "yes":"Si", "no":"No", From 35afbf6e44b93550dbf0148812ca6895ad7716a3 Mon Sep 17 00:00:00 2001 From: Jannik Tappert <38758606+CodeTappert@users.noreply.github.com> Date: Thu, 16 May 2024 11:13:57 +0200 Subject: [PATCH 44/46] Added german egg localization (#955) * Added german egg localization * Changed pull back to english since there isnt enough space for a german word that makes sense and most if not all german players understand "pull" * This comma was too much --- src/locales/de/egg.ts | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/src/locales/de/egg.ts b/src/locales/de/egg.ts index 358c1b4a503..3950d6729ff 100644 --- a/src/locales/de/egg.ts +++ b/src/locales/de/egg.ts @@ -1,21 +1,21 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const egg: SimpleTranslationEntries = { - "egg": "Egg", - "greatTier": "Rare", - "ultraTier": "Epic", - "masterTier": "Legendary", - "defaultTier": "Common", - "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", - "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", - "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", - "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", - "gachaTypeLegendary": "Legendary Rate Up", - "gachaTypeMove": "Rare Egg Move Rate Up", - "gachaTypeShiny": "Shiny Rate Up", - "selectMachine": "Select a machine.", - "notEnoughVouchers": "You don't have enough vouchers!", - "tooManyEggs": "You have too many eggs!", + "egg": "Ei", + "greatTier": "Selten", + "ultraTier": "Episch", + "masterTier": "Legendär", + "defaultTier": "Gewöhnlich", + "hatchWavesMessageSoon": "Man kann schon etwas hören! Es wird wohl bald schlüpfen!", + "hatchWavesMessageClose": "Manchmal bewegt es sich! Es braucht wohl noch ein Weilchen.", + "hatchWavesMessageNotClose": "Was wird da wohl schlüpfen? Es wird sicher noch lange dauern.", + "hatchWavesMessageLongTime": "Dieses Ei braucht sicher noch sehr viel Zeit.", + "gachaTypeLegendary": "Erhöhte Chance auf legendäre Eier", + "gachaTypeMove": "Erhöhte Chance auf Eier mit seltenen Attacken", + "gachaTypeShiny": "Erhöhte Chance auf schillernde Eier", + "selectMachine": "Wähle eine Maschine", + "notEnoughVouchers": "Du hast nicht genug Ei-Gutscheine!", + "tooManyEggs": "Du hast schon zu viele Eier!", "pull": "Pull", "pulls": "Pulls" } as const; \ No newline at end of file From 3f40225d4bb93d7539ced7efc6b7fea491472b7a Mon Sep 17 00:00:00 2001 From: Alessandro Bruzzese <69127023+Bruzzii@users.noreply.github.com> Date: Thu, 16 May 2024 11:14:21 +0200 Subject: [PATCH 45/46] Update italian weather.ts (#956) --- src/locales/it/weather.ts | 58 +++++++++++++++++++-------------------- 1 file changed, 29 insertions(+), 29 deletions(-) diff --git a/src/locales/it/weather.ts b/src/locales/it/weather.ts index 999613f1566..d5f0f440e1e 100644 --- a/src/locales/it/weather.ts +++ b/src/locales/it/weather.ts @@ -4,41 +4,41 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; * The weather namespace holds text displayed when weather is active during a battle */ export const weather: SimpleTranslationEntries = { - "sunnyStartMessage": "The sunlight got bright!", - "sunnyLapseMessage": "The sunlight is strong.", - "sunnyClearMessage": "The sunlight faded.", + "sunnyStartMessage": "La luce solare è intensa!", + "sunnyLapseMessage": "La luce solare è forte.", + "sunnyClearMessage": "La luce solare si sta attenuando.", - "rainStartMessage": "A downpour started!", - "rainLapseMessage": "The downpour continues.", - "rainClearMessage": "The rain stopped.", + "rainStartMessage": "Ha iniziato a piovere!", + "rainLapseMessage": "La pioggia continua.", + "rainClearMessage": "Ha smesso di piovere.", - "sandstormStartMessage": "A sandstorm brewed!", - "sandstormLapseMessage": "The sandstorm rages.", - "sandstormClearMessage": "The sandstorm subsided.", - "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is buffeted\nby the sandstorm!", + "sandstormStartMessage": "Si è scatenata una tempesta di sabbia!", + "sandstormLapseMessage": "La tempesta di sabbia infuria.", + "sandstormClearMessage": "La tempesta di sabbia si è placata.", + "sandstormDamageMessage": "{{pokemonPrefix}}{{pokemonName}} è stato colpito\ndalla tempesta di sabbia!", - "hailStartMessage": "It started to hail!", - "hailLapseMessage": "Hail continues to fall.", - "hailClearMessage": "The hail stopped.", - "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} is pelted\nby the hail!", + "hailStartMessage": "Ha iniziato a grandinare!", + "hailLapseMessage": "La grandine continua a cadere.", + "hailClearMessage": "Ha smesso di grandinare.", + "hailDamageMessage": "{{pokemonPrefix}}{{pokemonName}} è stato colpito\ndalla grandine!", - "snowStartMessage": "It started to snow!", - "snowLapseMessage": "The snow is falling down.", - "snowClearMessage": "The snow stopped.", + "snowStartMessage": "Ha iniziato a nevicare!", + "snowLapseMessage": "La neve sta continuando a cadere.", + "snowClearMessage": "Ha smesso di nevicare!.", - "fogStartMessage": "A thick fog emerged!", - "fogLapseMessage": "The fog continues.", - "fogClearMessage": "The fog disappeared.", + "fogStartMessage": "È emersa una fitta nebbia!", + "fogLapseMessage": "La nebbia continua.", + "fogClearMessage": "La nebbia è scomparsa.", - "heavyRainStartMessage": "A heavy downpour started!", - "heavyRainLapseMessage": "The heavy downpour continues.", - "heavyRainClearMessage": "The heavy rain stopped.", + "heavyRainStartMessage": "Ha iniziato a piovere forte!", + "heavyRainLapseMessage": "La pioggia battente continua.", + "heavyRainClearMessage": "La pioggia battente è cessata.", - "harshSunStartMessage": "The sunlight got hot!", - "harshSunLapseMessage": "The sun is scorching hot.", - "harshSunClearMessage": "The harsh sunlight faded.", + "harshSunStartMessage": "La luce solare è molto intensa!", + "harshSunLapseMessage": "La luce solare è estremamente calda.", + "harshSunClearMessage": "La luce solare si sta attenuando.", - "strongWindsStartMessage": "A heavy wind began!", - "strongWindsLapseMessage": "The wind blows intensely.", - "strongWindsClearMessage": "The heavy wind stopped." + "strongWindsStartMessage": "È apparsa una corrente d'aria misteriosa!", + "strongWindsLapseMessage": "La corrente d'aria soffia intensamente.", + "strongWindsClearMessage": "La corrente d'aria è cessata." } \ No newline at end of file From 5fe69fff9ce1b6ec3c790a79ec7f66c21c4ac69d Mon Sep 17 00:00:00 2001 From: Alessandro Bruzzese <69127023+Bruzzii@users.noreply.github.com> Date: Thu, 16 May 2024 11:19:10 +0200 Subject: [PATCH 46/46] Update italian egg.ts (#958) --- src/locales/it/egg.ts | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) diff --git a/src/locales/it/egg.ts b/src/locales/it/egg.ts index 358c1b4a503..5634a2ae15b 100644 --- a/src/locales/it/egg.ts +++ b/src/locales/it/egg.ts @@ -1,21 +1,21 @@ import { SimpleTranslationEntries } from "#app/plugins/i18n"; export const egg: SimpleTranslationEntries = { - "egg": "Egg", - "greatTier": "Rare", - "ultraTier": "Epic", - "masterTier": "Legendary", - "defaultTier": "Common", - "hatchWavesMessageSoon": "Sounds can be heard coming from inside! It will hatch soon!", - "hatchWavesMessageClose": "It appears to move occasionally. It may be close to hatching.", - "hatchWavesMessageNotClose": "What will hatch from this? It doesn't seem close to hatching.", - "hatchWavesMessageLongTime": "It looks like this Egg will take a long time to hatch.", - "gachaTypeLegendary": "Legendary Rate Up", - "gachaTypeMove": "Rare Egg Move Rate Up", - "gachaTypeShiny": "Shiny Rate Up", - "selectMachine": "Select a machine.", - "notEnoughVouchers": "You don't have enough vouchers!", - "tooManyEggs": "You have too many eggs!", - "pull": "Pull", - "pulls": "Pulls" + "egg": "Uovo", + "defaultTier": "Comune", + "greatTier": "Raro", + "ultraTier": "Epico", + "masterTier": "Leggendario", + "hatchWavesMessageSoon": "Si sentono dei suoni provenienti dall'interno! Si schiuderà presto!", + "hatchWavesMessageClose": "Sembra muoversi di tanto in tanto. Potrebbe essere prossimo alla schiusa.", + "hatchWavesMessageNotClose": "Cosa uscirà da qui? Non sembra si schiuderà presto.", + "hatchWavesMessageLongTime": "Sembra che questo uovo impiegherà molto tempo per schiudersi.", + "gachaTypeLegendary": "Tasso dei Leggendari Aumentato", + "gachaTypeMove": "Tasso delle Mosse Rare delle Uova Aumentato", + "gachaTypeShiny": "Tasso degli Shiny Aumentato", + "selectMachine": "Seleziona un distributore.", + "notEnoughVouchers": "Non hai abbastanza Biglietti!", + "tooManyEggs": "Hai troppe Uova!", + "pull": "Tiro", + "pulls": "Tiri" } as const; \ No newline at end of file