mirror of
https://github.com/pagefaultgames/pokerogue.git
synced 2025-07-01 14:02:18 +02:00
Reworked various effects that steal items
This commit is contained in:
parent
c607a73ebc
commit
b271dc724b
@ -2717,11 +2717,12 @@ export default class BattleScene extends SceneBase {
|
||||
}
|
||||
|
||||
/**
|
||||
* Try to transfer a held item to another pokemon.
|
||||
* Try to transfer a held item from source to target.
|
||||
* If the recepient already has the maximum amount allowed for this item, the transfer is cancelled.
|
||||
* The quantity to transfer is automatically capped at how much the recepient can take before reaching the maximum stack size for the item.
|
||||
* A transfer that moves a quantity smaller than what is specified in the transferQuantity parameter is still considered successful.
|
||||
* @param heldItemId {@linkcode HeldItemId} item to transfer
|
||||
* @param source {@linkcode Pokemon} giver in this transfer
|
||||
* @param target {@linkcode Pokemon} recepient in this transfer
|
||||
* @param playSound `true` to play a sound when transferring the item
|
||||
* @param transferQuantity How many items of the stack to transfer. Optional, defaults to `1`
|
||||
|
@ -35,7 +35,7 @@ import {
|
||||
} from "#app/data/moves/move";
|
||||
import { allMoves } from "../data-lists";
|
||||
import { ArenaTagSide } from "#app/data/arena-tag";
|
||||
import { BerryModifier, PokemonHeldItemModifier } from "#app/modifier/modifier";
|
||||
import { BerryModifier, type PokemonHeldItemModifier } from "#app/modifier/modifier";
|
||||
import { TerrainType } from "#app/data/terrain";
|
||||
import {
|
||||
SpeciesFormChangeAbilityTrigger,
|
||||
@ -91,6 +91,7 @@ import type Move from "#app/data/moves/move";
|
||||
import type { ArenaTrapTag, SuppressAbilitiesTag } from "#app/data/arena-tag";
|
||||
import { noAbilityTypeOverrideMoves } from "../moves/invalid-moves";
|
||||
import { HeldItemId } from "#enums/held-item-id";
|
||||
import { allHeldItems } from "#app/items/all-held-items";
|
||||
|
||||
export class BlockRecoilDamageAttr extends AbAttr {
|
||||
constructor() {
|
||||
@ -2540,17 +2541,11 @@ export class AllyStatMultiplierAbAttr extends AbAttr {
|
||||
* @extends AbAttr
|
||||
*/
|
||||
export class ExecutedMoveAbAttr extends AbAttr {
|
||||
canApplyExecutedMove(
|
||||
_pokemon: Pokemon,
|
||||
_simulated: boolean,
|
||||
): boolean {
|
||||
canApplyExecutedMove(_pokemon: Pokemon, _simulated: boolean): boolean {
|
||||
return true;
|
||||
}
|
||||
|
||||
applyExecutedMove(
|
||||
_pokemon: Pokemon,
|
||||
_simulated: boolean,
|
||||
): void {}
|
||||
applyExecutedMove(_pokemon: Pokemon, _simulated: boolean): void {}
|
||||
}
|
||||
|
||||
/**
|
||||
@ -2558,7 +2553,7 @@ export class ExecutedMoveAbAttr extends AbAttr {
|
||||
* @extends ExecutedMoveAbAttr
|
||||
*/
|
||||
export class GorillaTacticsAbAttr extends ExecutedMoveAbAttr {
|
||||
constructor(showAbility: boolean = false) {
|
||||
constructor(showAbility = false) {
|
||||
super(showAbility);
|
||||
}
|
||||
|
||||
@ -2575,7 +2570,7 @@ export class GorillaTacticsAbAttr extends ExecutedMoveAbAttr {
|
||||
|
||||
export class PostAttackStealHeldItemAbAttr extends PostAttackAbAttr {
|
||||
private stealCondition: PokemonAttackCondition | null;
|
||||
private stolenItem?: PokemonHeldItemModifier;
|
||||
private stolenItem?: HeldItemId;
|
||||
|
||||
constructor(stealCondition?: PokemonAttackCondition) {
|
||||
super();
|
||||
@ -2598,11 +2593,11 @@ export class PostAttackStealHeldItemAbAttr extends PostAttackAbAttr {
|
||||
hitResult < HitResult.NO_EFFECT &&
|
||||
(!this.stealCondition || this.stealCondition(pokemon, defender, move))
|
||||
) {
|
||||
const heldItems = this.getTargetHeldItems(defender).filter(i => i.isTransferable);
|
||||
const heldItems = defender.heldItemManager.getTransferableHeldItems();
|
||||
if (heldItems.length) {
|
||||
// Ensure that the stolen item in testing is the same as when the effect is applied
|
||||
this.stolenItem = heldItems[pokemon.randBattleSeedInt(heldItems.length)];
|
||||
if (globalScene.canTransferHeldItemModifier(this.stolenItem, pokemon)) {
|
||||
if (globalScene.canTransferHeldItem(this.stolenItem, defender, pokemon)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -2620,28 +2615,21 @@ export class PostAttackStealHeldItemAbAttr extends PostAttackAbAttr {
|
||||
_hitResult: HitResult,
|
||||
_args: any[],
|
||||
): void {
|
||||
const heldItems = this.getTargetHeldItems(defender).filter(i => i.isTransferable);
|
||||
const heldItems = defender.heldItemManager.getTransferableHeldItems();
|
||||
if (!this.stolenItem) {
|
||||
this.stolenItem = heldItems[pokemon.randBattleSeedInt(heldItems.length)];
|
||||
}
|
||||
if (globalScene.tryTransferHeldItemModifier(this.stolenItem, pokemon, false)) {
|
||||
if (globalScene.tryTransferHeldItem(this.stolenItem, defender, pokemon, false)) {
|
||||
globalScene.phaseManager.queueMessage(
|
||||
i18next.t("abilityTriggers:postAttackStealHeldItem", {
|
||||
pokemonNameWithAffix: getPokemonNameWithAffix(pokemon),
|
||||
defenderName: defender.name,
|
||||
stolenItemType: this.stolenItem.type.name,
|
||||
stolenItemType: allHeldItems[this.stolenItem].name,
|
||||
}),
|
||||
);
|
||||
}
|
||||
this.stolenItem = undefined;
|
||||
}
|
||||
|
||||
getTargetHeldItems(target: Pokemon): PokemonHeldItemModifier[] {
|
||||
return globalScene.findModifiers(
|
||||
m => m instanceof PokemonHeldItemModifier && m.pokemonId === target.id,
|
||||
target.isPlayer(),
|
||||
) as PokemonHeldItemModifier[];
|
||||
}
|
||||
}
|
||||
|
||||
export class PostAttackApplyStatusEffectAbAttr extends PostAttackAbAttr {
|
||||
@ -2762,7 +2750,7 @@ export class PostAttackApplyBattlerTagAbAttr extends PostAttackAbAttr {
|
||||
|
||||
export class PostDefendStealHeldItemAbAttr extends PostDefendAbAttr {
|
||||
private condition?: PokemonDefendCondition;
|
||||
private stolenItem?: PokemonHeldItemModifier;
|
||||
private stolenItem?: HeldItemId;
|
||||
|
||||
constructor(condition?: PokemonDefendCondition) {
|
||||
super();
|
||||
@ -2780,10 +2768,10 @@ export class PostDefendStealHeldItemAbAttr extends PostDefendAbAttr {
|
||||
_args: any[],
|
||||
): boolean {
|
||||
if (!simulated && hitResult < HitResult.NO_EFFECT && (!this.condition || this.condition(pokemon, attacker, move))) {
|
||||
const heldItems = this.getTargetHeldItems(attacker).filter(i => i.isTransferable);
|
||||
const heldItems = attacker.heldItemManager.getTransferableHeldItems();
|
||||
if (heldItems.length) {
|
||||
this.stolenItem = heldItems[pokemon.randBattleSeedInt(heldItems.length)];
|
||||
if (globalScene.canTransferHeldItemModifier(this.stolenItem, pokemon)) {
|
||||
if (globalScene.canTransferHeldItem(this.stolenItem, attacker, pokemon)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -2800,28 +2788,21 @@ export class PostDefendStealHeldItemAbAttr extends PostDefendAbAttr {
|
||||
_hitResult: HitResult,
|
||||
_args: any[],
|
||||
): void {
|
||||
const heldItems = this.getTargetHeldItems(attacker).filter(i => i.isTransferable);
|
||||
const heldItems = attacker.heldItemManager.getTransferableHeldItems();
|
||||
if (!this.stolenItem) {
|
||||
this.stolenItem = heldItems[pokemon.randBattleSeedInt(heldItems.length)];
|
||||
}
|
||||
if (globalScene.tryTransferHeldItemModifier(this.stolenItem, pokemon, false)) {
|
||||
if (globalScene.tryTransferHeldItem(this.stolenItem, attacker, pokemon, false)) {
|
||||
globalScene.phaseManager.queueMessage(
|
||||
i18next.t("abilityTriggers:postDefendStealHeldItem", {
|
||||
pokemonNameWithAffix: getPokemonNameWithAffix(pokemon),
|
||||
attackerName: attacker.name,
|
||||
stolenItemType: this.stolenItem.type.name,
|
||||
stolenItemType: allHeldItems[this.stolenItem].name,
|
||||
}),
|
||||
);
|
||||
}
|
||||
this.stolenItem = undefined;
|
||||
}
|
||||
|
||||
getTargetHeldItems(target: Pokemon): PokemonHeldItemModifier[] {
|
||||
return globalScene.findModifiers(
|
||||
m => m instanceof PokemonHeldItemModifier && m.pokemonId === target.id,
|
||||
target.isPlayer(),
|
||||
) as PokemonHeldItemModifier[];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@ -7782,7 +7763,7 @@ export function applyPreAttackAbAttrs(
|
||||
export function applyExecutedMoveAbAttrs(
|
||||
attrType: Constructor<ExecutedMoveAbAttr>,
|
||||
pokemon: Pokemon,
|
||||
simulated: boolean = false,
|
||||
simulated = false,
|
||||
...args: any[]
|
||||
): void {
|
||||
applyAbAttrsInternal<ExecutedMoveAbAttr>(
|
||||
|
@ -2559,16 +2559,18 @@ export class StealHeldItemChanceAttr extends MoveEffectAttr {
|
||||
return false;
|
||||
}
|
||||
|
||||
const heldItems = this.getTargetHeldItems(target).filter((i) => i.isTransferable);
|
||||
const heldItems = target.heldItemManager.getTransferableHeldItems();
|
||||
if (!heldItems.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const poolType = target.isPlayer() ? ModifierPoolType.PLAYER : target.hasTrainer() ? ModifierPoolType.TRAINER : ModifierPoolType.WILD;
|
||||
const highestItemTier = heldItems.map((m) => m.type.getOrInferTier(poolType)).reduce((highestTier, tier) => Math.max(tier!, highestTier), 0); // TODO: is the bang after tier correct?
|
||||
const tierHeldItems = heldItems.filter((m) => m.type.getOrInferTier(poolType) === highestItemTier);
|
||||
const stolenItem = tierHeldItems[user.randBattleSeedInt(tierHeldItems.length)];
|
||||
if (!globalScene.tryTransferHeldItemModifier(stolenItem, user, false)) {
|
||||
const stolenItem = heldItems[user.randBattleSeedInt(heldItems.length)];
|
||||
|
||||
// const poolType = target.isPlayer() ? ModifierPoolType.PLAYER : target.hasTrainer() ? ModifierPoolType.TRAINER : ModifierPoolType.WILD;
|
||||
// const highestItemTier = heldItems.map((m) => m.type.getOrInferTier(poolType)).reduce((highestTier, tier) => Math.max(tier!, highestTier), 0); // TODO: is the bang after tier correct?
|
||||
// const tierHeldItems = heldItems.filter((m) => m.type.getOrInferTier(poolType) === highestItemTier);
|
||||
// const stolenItem = tierHeldItems[user.randBattleSeedInt(tierHeldItems.length)];
|
||||
if (!globalScene.tryTransferHeldItem(stolenItem, target, user, false)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -2576,18 +2578,13 @@ export class StealHeldItemChanceAttr extends MoveEffectAttr {
|
||||
return true;
|
||||
}
|
||||
|
||||
getTargetHeldItems(target: Pokemon): PokemonHeldItemModifier[] {
|
||||
return globalScene.findModifiers(m => m instanceof PokemonHeldItemModifier
|
||||
&& m.pokemonId === target.id, target.isPlayer()) as PokemonHeldItemModifier[];
|
||||
}
|
||||
|
||||
getUserBenefitScore(user: Pokemon, target: Pokemon, move: Move): number {
|
||||
const heldItems = this.getTargetHeldItems(target);
|
||||
const heldItems = target.heldItemManager.getTransferableHeldItems();
|
||||
return heldItems.length ? 5 : 0;
|
||||
}
|
||||
|
||||
getTargetBenefitScore(user: Pokemon, target: Pokemon, move: Move): number {
|
||||
const heldItems = this.getTargetHeldItems(target);
|
||||
const heldItems = target.heldItemManager.getTransferableHeldItems();
|
||||
return heldItems.length ? -5 : 0;
|
||||
}
|
||||
}
|
||||
|
@ -35,6 +35,24 @@ export class PokemonItemManager {
|
||||
return Object.keys(this.heldItems).map(k => Number(k));
|
||||
}
|
||||
|
||||
getTransferableHeldItems(): number[] {
|
||||
return Object.keys(this.heldItems)
|
||||
.filter(k => allHeldItems[k].isTransferable)
|
||||
.map(k => Number(k));
|
||||
}
|
||||
|
||||
getStealableHeldItems(): number[] {
|
||||
return Object.keys(this.heldItems)
|
||||
.filter(k => allHeldItems[k].isStealable)
|
||||
.map(k => Number(k));
|
||||
}
|
||||
|
||||
getSuppressableHeldItems(): number[] {
|
||||
return Object.keys(this.heldItems)
|
||||
.filter(k => allHeldItems[k].isSuppressable)
|
||||
.map(k => Number(k));
|
||||
}
|
||||
|
||||
hasItem(itemType: HeldItemId): boolean {
|
||||
return itemType in this.heldItems;
|
||||
}
|
||||
|
@ -47,7 +47,7 @@ export abstract class ItemTransferHeldItem extends HeldItem {
|
||||
|
||||
// TODO: Change this logic to use held items
|
||||
const transferredModifierTypes: HeldItemId[] = [];
|
||||
const heldItems = targetPokemon.heldItemManager.getHeldItemKeys();
|
||||
const heldItems = targetPokemon.heldItemManager.getTransferableHeldItems();
|
||||
|
||||
for (let i = 0; i < transferredItemCount; i++) {
|
||||
if (!heldItems.length) {
|
||||
@ -56,7 +56,7 @@ export abstract class ItemTransferHeldItem extends HeldItem {
|
||||
const randItemIndex = pokemon.randBattleSeedInt(heldItems.length);
|
||||
const randItem = heldItems[randItemIndex];
|
||||
// TODO: Fix this after updating the various methods in battle-scene.ts
|
||||
if (globalScene.tryTransferHeldItemModifier(randItem, pokemon, false)) {
|
||||
if (globalScene.tryTransferHeldItem(randItem, targetPokemon, pokemon, false)) {
|
||||
transferredModifierTypes.push(randItem);
|
||||
heldItems.splice(randItemIndex, 1);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user