mirror of
https://github.com/smogon/pokemon-showdown.git
synced 2026-04-01 14:46:04 -05:00
For side conditions, `onStart`/`onRestart`/`onResidual`/`onEnd` have been renamed `onSideStart`/`onSideRestart`/`onSideResidual`/`onSideEnd`, with the `onResidualOrder` properties renamed `onSideResidualOrder`. For field conditions, `onStart`/`onRestart`/`onResidual`/`onEnd` have been renamed `onFieldStart`/`onFieldRestart`/`onFieldResidual`/`onFieldEnd`, with the `onResidualOrder` properties renamed `onFieldResidualOrder`. (The `onField` and `onSide` part helps make it clear to the type system that the first argument is a Field or Side, not a Pokemon.) Side and field conditions can now use `onResidual` to tick separately on each pokemon in Speed order. `onResidualOrder` (the per-pokemon tick) can be timed separate from `onSideResidualOrder` (the per-condition tick), allowing conditions to end at a different priority than they tick per-pokemon. Relatedly, `onTeamPreview` and `onStart` in formats now need to be `onFieldTeamPreview` and `onFieldStart`. Unrelatedly, `effectData` has been renamed `effectState`, and the corresponding state containers (`pokemon.statusData`, `pokemon.speciesData`, `pokemon.itemData`, `pokemon.abilityData`, `field.weatherData`, `field.terrainData`) have been similarly renamed. I renamed the types a while ago, but I was holding off renaming the fields because it would be a breaking change. But this is a breaking change anyway, so we might as well do it now. Note: `onResidual` will tick even on `onSideEnd` turns, although `onSideResidual` won't. When refactoring weather, remember to check `this.state.duration` so you don't deal weather damage on the ending turn. Intended as a better fix for #8216
47 lines
1.5 KiB
TypeScript
47 lines
1.5 KiB
TypeScript
export const Scripts: ModdedBattleScriptsData = {
|
|
gen: 8,
|
|
field: {
|
|
suppressingWeather() {
|
|
for (const pokemon of this.battle.getAllActive()) {
|
|
const innates = Object.keys(pokemon.volatiles).filter(x => x.startsWith('ability:'));
|
|
if (pokemon && !pokemon.ignoringAbility() &&
|
|
(pokemon.getAbility().suppressWeather || innates.some(x => this.battle.dex.abilities.get(x).suppressWeather))) {
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
},
|
|
},
|
|
pokemon: {
|
|
hasAbility(ability) {
|
|
if (this.ignoringAbility()) return false;
|
|
if (Array.isArray(ability)) return ability.some(abil => this.hasAbility(abil));
|
|
const abilityid = this.battle.toID(ability);
|
|
return this.ability === abilityid || !!this.volatiles['ability:' + abilityid];
|
|
},
|
|
ignoringAbility() {
|
|
// Check if any active pokemon have the ability Neutralizing Gas
|
|
let neutralizinggas = false;
|
|
for (const pokemon of this.battle.getAllActive()) {
|
|
// can't use hasAbility because it would lead to infinite recursion
|
|
if (
|
|
(pokemon.ability === ('neutralizinggas' as ID) || pokemon.m.abils?.includes('ability:neutralizinggas')) &&
|
|
!pokemon.volatiles['gastroacid'] && !pokemon.abilityState.ending
|
|
) {
|
|
neutralizinggas = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
return !!(
|
|
(this.battle.gen >= 5 && !this.isActive) ||
|
|
((this.volatiles['gastroacid'] ||
|
|
(neutralizinggas && (this.ability !== ('neutralizinggas' as ID) ||
|
|
this.m.abils?.includes('ability:neutralizinggas'))
|
|
)) && !this.getAbility().isPermanent
|
|
)
|
|
);
|
|
},
|
|
},
|
|
};
|