@pkmn/sim 0.8.3 → 0.8.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (286) hide show
  1. package/build/cjs/config/formats.js +163 -212
  2. package/build/cjs/config/formats.js.map +1 -1
  3. package/build/cjs/data/abilities.js +370 -165
  4. package/build/cjs/data/abilities.js.map +1 -1
  5. package/build/cjs/data/conditions.js +0 -3
  6. package/build/cjs/data/conditions.js.map +1 -1
  7. package/build/cjs/data/formats-data.js +330 -312
  8. package/build/cjs/data/formats-data.js.map +1 -1
  9. package/build/cjs/data/items.js +2 -2
  10. package/build/cjs/data/items.js.map +1 -1
  11. package/build/cjs/data/legality.js +424 -104
  12. package/build/cjs/data/legality.js.map +1 -1
  13. package/build/cjs/data/mods/gen1/formats-data.js +22 -22
  14. package/build/cjs/data/mods/gen1/moves.js +6 -8
  15. package/build/cjs/data/mods/gen1/moves.js.map +1 -1
  16. package/build/cjs/data/mods/gen2/formats-data.js +43 -43
  17. package/build/cjs/data/mods/gen2/formats-data.js.map +1 -1
  18. package/build/cjs/data/mods/gen2/moves.js +4 -7
  19. package/build/cjs/data/mods/gen2/moves.js.map +1 -1
  20. package/build/cjs/data/mods/gen3/abilities.js +6 -5
  21. package/build/cjs/data/mods/gen3/abilities.js.map +1 -1
  22. package/build/cjs/data/mods/gen3/formats-data.js +32 -32
  23. package/build/cjs/data/mods/gen3/formats-data.js.map +1 -1
  24. package/build/cjs/data/mods/gen3/moves.js +15 -10
  25. package/build/cjs/data/mods/gen3/moves.js.map +1 -1
  26. package/build/cjs/data/mods/gen3/scripts.js +11 -6
  27. package/build/cjs/data/mods/gen3/scripts.js.map +1 -1
  28. package/build/cjs/data/mods/gen4/abilities.js +8 -2
  29. package/build/cjs/data/mods/gen4/abilities.js.map +1 -1
  30. package/build/cjs/data/mods/gen4/moves.js +49 -45
  31. package/build/cjs/data/mods/gen4/moves.js.map +1 -1
  32. package/build/cjs/data/mods/gen4/scripts.js +11 -6
  33. package/build/cjs/data/mods/gen4/scripts.js.map +1 -1
  34. package/build/cjs/data/mods/gen5/abilities.js +1 -0
  35. package/build/cjs/data/mods/gen5/abilities.js.map +1 -1
  36. package/build/cjs/data/mods/gen5/moves.js +44 -66
  37. package/build/cjs/data/mods/gen5/moves.js.map +1 -1
  38. package/build/cjs/data/mods/gen6/abilities.js +1 -1
  39. package/build/cjs/data/mods/gen6/abilities.js.map +1 -1
  40. package/build/cjs/data/mods/gen6/moves.js +1 -1
  41. package/build/cjs/data/mods/gen6/moves.js.map +1 -1
  42. package/build/cjs/data/mods/gen7/abilities.js +2 -2
  43. package/build/cjs/data/mods/gen7/abilities.js.map +1 -1
  44. package/build/cjs/data/mods/gen7/moves.js +21 -9
  45. package/build/cjs/data/mods/gen7/moves.js.map +1 -1
  46. package/build/cjs/data/mods/gen8/abilities.js +3 -1
  47. package/build/cjs/data/mods/gen8/abilities.js.map +1 -1
  48. package/build/cjs/data/mods/gen8/moves.js +6 -2
  49. package/build/cjs/data/mods/gen8/moves.js.map +1 -1
  50. package/build/cjs/data/moves.js +760 -770
  51. package/build/cjs/data/moves.js.map +1 -1
  52. package/build/cjs/data/rulesets.js +33 -56
  53. package/build/cjs/data/rulesets.js.map +1 -1
  54. package/build/cjs/data/text/abilities.js +34 -12
  55. package/build/cjs/data/text/abilities.js.map +1 -1
  56. package/build/cjs/data/text/moves.js +9 -9
  57. package/build/cjs/data/text/moves.js.map +1 -1
  58. package/build/cjs/sim/battle-actions.js +21 -21
  59. package/build/cjs/sim/battle-actions.js.map +1 -1
  60. package/build/cjs/sim/battle.js +4 -5
  61. package/build/cjs/sim/battle.js.map +1 -1
  62. package/build/cjs/sim/dex-abilities.d.ts +11 -2
  63. package/build/cjs/sim/dex-abilities.js +1 -0
  64. package/build/cjs/sim/dex-abilities.js.map +1 -1
  65. package/build/cjs/sim/dex-conditions.d.ts +6 -0
  66. package/build/cjs/sim/dex-conditions.js.map +1 -1
  67. package/build/cjs/sim/dex-formats.d.ts +2 -0
  68. package/build/cjs/sim/dex-formats.js +1 -0
  69. package/build/cjs/sim/dex-formats.js.map +1 -1
  70. package/build/cjs/sim/dex-moves.d.ts +1 -4
  71. package/build/cjs/sim/dex-moves.js +0 -1
  72. package/build/cjs/sim/dex-moves.js.map +1 -1
  73. package/build/cjs/sim/exported-global-types.d.ts +2 -2
  74. package/build/cjs/sim/global-types.d.ts +2 -2
  75. package/build/cjs/sim/pokemon.js +7 -4
  76. package/build/cjs/sim/pokemon.js.map +1 -1
  77. package/build/cjs/sim/team-validator.js +1 -1
  78. package/build/cjs/sim/team-validator.js.map +1 -1
  79. package/build/cjs/sim/tools/runner.js +1 -1
  80. package/build/cjs/sim/tools/runner.js.map +1 -1
  81. package/build/esm/config/formats.mjs +163 -212
  82. package/build/esm/config/formats.mjs.map +1 -1
  83. package/build/esm/data/abilities.mjs +370 -165
  84. package/build/esm/data/abilities.mjs.map +1 -1
  85. package/build/esm/data/conditions.mjs +0 -3
  86. package/build/esm/data/conditions.mjs.map +1 -1
  87. package/build/esm/data/formats-data.mjs +330 -312
  88. package/build/esm/data/formats-data.mjs.map +1 -1
  89. package/build/esm/data/items.mjs +2 -2
  90. package/build/esm/data/items.mjs.map +1 -1
  91. package/build/esm/data/legality.mjs +424 -104
  92. package/build/esm/data/legality.mjs.map +1 -1
  93. package/build/esm/data/mods/gen1/formats-data.mjs +22 -22
  94. package/build/esm/data/mods/gen1/moves.mjs +6 -8
  95. package/build/esm/data/mods/gen1/moves.mjs.map +1 -1
  96. package/build/esm/data/mods/gen2/formats-data.mjs +43 -43
  97. package/build/esm/data/mods/gen2/formats-data.mjs.map +1 -1
  98. package/build/esm/data/mods/gen2/moves.mjs +4 -7
  99. package/build/esm/data/mods/gen2/moves.mjs.map +1 -1
  100. package/build/esm/data/mods/gen3/abilities.mjs +6 -5
  101. package/build/esm/data/mods/gen3/abilities.mjs.map +1 -1
  102. package/build/esm/data/mods/gen3/formats-data.mjs +32 -32
  103. package/build/esm/data/mods/gen3/formats-data.mjs.map +1 -1
  104. package/build/esm/data/mods/gen3/moves.mjs +15 -10
  105. package/build/esm/data/mods/gen3/moves.mjs.map +1 -1
  106. package/build/esm/data/mods/gen3/scripts.mjs +11 -6
  107. package/build/esm/data/mods/gen3/scripts.mjs.map +1 -1
  108. package/build/esm/data/mods/gen4/abilities.mjs +8 -2
  109. package/build/esm/data/mods/gen4/abilities.mjs.map +1 -1
  110. package/build/esm/data/mods/gen4/moves.mjs +49 -45
  111. package/build/esm/data/mods/gen4/moves.mjs.map +1 -1
  112. package/build/esm/data/mods/gen4/scripts.mjs +11 -6
  113. package/build/esm/data/mods/gen4/scripts.mjs.map +1 -1
  114. package/build/esm/data/mods/gen5/abilities.mjs +1 -0
  115. package/build/esm/data/mods/gen5/abilities.mjs.map +1 -1
  116. package/build/esm/data/mods/gen5/moves.mjs +44 -66
  117. package/build/esm/data/mods/gen5/moves.mjs.map +1 -1
  118. package/build/esm/data/mods/gen6/abilities.mjs +1 -1
  119. package/build/esm/data/mods/gen6/abilities.mjs.map +1 -1
  120. package/build/esm/data/mods/gen6/moves.mjs +1 -1
  121. package/build/esm/data/mods/gen6/moves.mjs.map +1 -1
  122. package/build/esm/data/mods/gen7/abilities.mjs +2 -2
  123. package/build/esm/data/mods/gen7/abilities.mjs.map +1 -1
  124. package/build/esm/data/mods/gen7/moves.mjs +21 -9
  125. package/build/esm/data/mods/gen7/moves.mjs.map +1 -1
  126. package/build/esm/data/mods/gen8/abilities.mjs +3 -1
  127. package/build/esm/data/mods/gen8/abilities.mjs.map +1 -1
  128. package/build/esm/data/mods/gen8/moves.mjs +6 -2
  129. package/build/esm/data/mods/gen8/moves.mjs.map +1 -1
  130. package/build/esm/data/moves.mjs +760 -770
  131. package/build/esm/data/moves.mjs.map +1 -1
  132. package/build/esm/data/rulesets.mjs +33 -56
  133. package/build/esm/data/rulesets.mjs.map +1 -1
  134. package/build/esm/data/text/abilities.mjs +34 -12
  135. package/build/esm/data/text/abilities.mjs.map +1 -1
  136. package/build/esm/data/text/moves.mjs +9 -9
  137. package/build/esm/data/text/moves.mjs.map +1 -1
  138. package/build/esm/sim/battle-actions.mjs +21 -21
  139. package/build/esm/sim/battle-actions.mjs.map +1 -1
  140. package/build/esm/sim/battle.mjs +4 -5
  141. package/build/esm/sim/battle.mjs.map +1 -1
  142. package/build/esm/sim/dex-abilities.d.mts +11 -2
  143. package/build/esm/sim/dex-abilities.mjs +1 -0
  144. package/build/esm/sim/dex-abilities.mjs.map +1 -1
  145. package/build/esm/sim/dex-conditions.d.mts +6 -0
  146. package/build/esm/sim/dex-conditions.mjs.map +1 -1
  147. package/build/esm/sim/dex-formats.d.mts +2 -0
  148. package/build/esm/sim/dex-formats.mjs +1 -0
  149. package/build/esm/sim/dex-formats.mjs.map +1 -1
  150. package/build/esm/sim/dex-moves.d.mts +1 -4
  151. package/build/esm/sim/dex-moves.mjs +0 -1
  152. package/build/esm/sim/dex-moves.mjs.map +1 -1
  153. package/build/esm/sim/exported-global-types.d.mts +2 -2
  154. package/build/esm/sim/global-types.d.mts +2 -2
  155. package/build/esm/sim/pokemon.mjs +7 -4
  156. package/build/esm/sim/pokemon.mjs.map +1 -1
  157. package/build/esm/sim/team-validator.mjs +1 -1
  158. package/build/esm/sim/team-validator.mjs.map +1 -1
  159. package/build/esm/sim/tools/runner.mjs +1 -1
  160. package/build/esm/sim/tools/runner.mjs.map +1 -1
  161. package/package.json +1 -1
  162. package/build/types/config/formats.d.ts +0 -1
  163. package/build/types/data/abilities.d.ts +0 -3
  164. package/build/types/data/aliases.d.ts +0 -3
  165. package/build/types/data/conditions.d.ts +0 -3
  166. package/build/types/data/formats-data.d.ts +0 -3
  167. package/build/types/data/index.d.ts +0 -11
  168. package/build/types/data/items.d.ts +0 -3
  169. package/build/types/data/learnsets.d.ts +0 -3
  170. package/build/types/data/legality.d.ts +0 -3
  171. package/build/types/data/mods/gen1/conditions.d.ts +0 -12
  172. package/build/types/data/mods/gen1/formats-data.d.ts +0 -3
  173. package/build/types/data/mods/gen1/index.d.ts +0 -7
  174. package/build/types/data/mods/gen1/moves.d.ts +0 -7
  175. package/build/types/data/mods/gen1/pokedex.d.ts +0 -3
  176. package/build/types/data/mods/gen1/rulesets.d.ts +0 -3
  177. package/build/types/data/mods/gen1/scripts.d.ts +0 -6
  178. package/build/types/data/mods/gen1/typechart.d.ts +0 -10
  179. package/build/types/data/mods/gen2/conditions.d.ts +0 -3
  180. package/build/types/data/mods/gen2/formats-data.d.ts +0 -3
  181. package/build/types/data/mods/gen2/index.d.ts +0 -8
  182. package/build/types/data/mods/gen2/items.d.ts +0 -3
  183. package/build/types/data/mods/gen2/learnsets.d.ts +0 -3
  184. package/build/types/data/mods/gen2/legality.d.ts +0 -3
  185. package/build/types/data/mods/gen2/moves.d.ts +0 -6
  186. package/build/types/data/mods/gen2/pokedex.d.ts +0 -3
  187. package/build/types/data/mods/gen2/rulesets.d.ts +0 -3
  188. package/build/types/data/mods/gen2/scripts.d.ts +0 -4
  189. package/build/types/data/mods/gen2/typechart.d.ts +0 -3
  190. package/build/types/data/mods/gen3/abilities.d.ts +0 -3
  191. package/build/types/data/mods/gen3/conditions.d.ts +0 -3
  192. package/build/types/data/mods/gen3/formats-data.d.ts +0 -3
  193. package/build/types/data/mods/gen3/index.d.ts +0 -7
  194. package/build/types/data/mods/gen3/items.d.ts +0 -3
  195. package/build/types/data/mods/gen3/moves.d.ts +0 -6
  196. package/build/types/data/mods/gen3/rulesets.d.ts +0 -3
  197. package/build/types/data/mods/gen3/scripts.d.ts +0 -1
  198. package/build/types/data/mods/gen4/abilities.d.ts +0 -3
  199. package/build/types/data/mods/gen4/conditions.d.ts +0 -3
  200. package/build/types/data/mods/gen4/formats-data.d.ts +0 -3
  201. package/build/types/data/mods/gen4/index.d.ts +0 -8
  202. package/build/types/data/mods/gen4/items.d.ts +0 -3
  203. package/build/types/data/mods/gen4/moves.d.ts +0 -3
  204. package/build/types/data/mods/gen4/pokedex.d.ts +0 -3
  205. package/build/types/data/mods/gen4/rulesets.d.ts +0 -3
  206. package/build/types/data/mods/gen4/scripts.d.ts +0 -1
  207. package/build/types/data/mods/gen5/abilities.d.ts +0 -3
  208. package/build/types/data/mods/gen5/conditions.d.ts +0 -3
  209. package/build/types/data/mods/gen5/formats-data.d.ts +0 -3
  210. package/build/types/data/mods/gen5/index.d.ts +0 -9
  211. package/build/types/data/mods/gen5/items.d.ts +0 -3
  212. package/build/types/data/mods/gen5/moves.d.ts +0 -3
  213. package/build/types/data/mods/gen5/pokedex.d.ts +0 -3
  214. package/build/types/data/mods/gen5/rulesets.d.ts +0 -3
  215. package/build/types/data/mods/gen5/scripts.d.ts +0 -1
  216. package/build/types/data/mods/gen5/typechart.d.ts +0 -3
  217. package/build/types/data/mods/gen6/abilities.d.ts +0 -3
  218. package/build/types/data/mods/gen6/conditions.d.ts +0 -3
  219. package/build/types/data/mods/gen6/formats-data.d.ts +0 -3
  220. package/build/types/data/mods/gen6/index.d.ts +0 -8
  221. package/build/types/data/mods/gen6/items.d.ts +0 -3
  222. package/build/types/data/mods/gen6/learnsets.d.ts +0 -3
  223. package/build/types/data/mods/gen6/legality.d.ts +0 -3
  224. package/build/types/data/mods/gen6/moves.d.ts +0 -3
  225. package/build/types/data/mods/gen6/pokedex.d.ts +0 -3
  226. package/build/types/data/mods/gen6/scripts.d.ts +0 -1
  227. package/build/types/data/mods/gen6/typechart.d.ts +0 -3
  228. package/build/types/data/mods/gen7/abilities.d.ts +0 -3
  229. package/build/types/data/mods/gen7/formats-data.d.ts +0 -3
  230. package/build/types/data/mods/gen7/index.d.ts +0 -7
  231. package/build/types/data/mods/gen7/items.d.ts +0 -3
  232. package/build/types/data/mods/gen7/moves.d.ts +0 -3
  233. package/build/types/data/mods/gen7/pokedex.d.ts +0 -3
  234. package/build/types/data/mods/gen7/rulesets.d.ts +0 -3
  235. package/build/types/data/mods/gen7/scripts.d.ts +0 -1
  236. package/build/types/data/mods/gen8/abilities.d.ts +0 -3
  237. package/build/types/data/mods/gen8/formats-data.d.ts +0 -3
  238. package/build/types/data/mods/gen8/index.d.ts +0 -7
  239. package/build/types/data/mods/gen8/items.d.ts +0 -3
  240. package/build/types/data/mods/gen8/learnsets.d.ts +0 -3
  241. package/build/types/data/mods/gen8/legality.d.ts +0 -3
  242. package/build/types/data/mods/gen8/moves.d.ts +0 -3
  243. package/build/types/data/mods/gen8/pokedex.d.ts +0 -3
  244. package/build/types/data/mods/gen8/rulesets.d.ts +0 -3
  245. package/build/types/data/mods/gen8/scripts.d.ts +0 -1
  246. package/build/types/data/moves.d.ts +0 -3
  247. package/build/types/data/natures.d.ts +0 -3
  248. package/build/types/data/pokedex.d.ts +0 -3
  249. package/build/types/data/pokemongo.d.ts +0 -31
  250. package/build/types/data/rulesets.d.ts +0 -3
  251. package/build/types/data/scripts.d.ts +0 -1
  252. package/build/types/data/tags.d.ts +0 -15
  253. package/build/types/data/text/abilities.d.ts +0 -3
  254. package/build/types/data/text/default.d.ts +0 -3
  255. package/build/types/data/text/items.d.ts +0 -3
  256. package/build/types/data/text/moves.d.ts +0 -3
  257. package/build/types/data/typechart.d.ts +0 -3
  258. package/build/types/lib/index.d.ts +0 -2
  259. package/build/types/lib/streams.d.ts +0 -1
  260. package/build/types/lib/utils.d.ts +0 -139
  261. package/build/types/sim/battle-actions.d.ts +0 -90
  262. package/build/types/sim/battle-queue.d.ts +0 -164
  263. package/build/types/sim/battle-stream.d.ts +0 -67
  264. package/build/types/sim/battle.d.ts +0 -396
  265. package/build/types/sim/dex-abilities.d.ts +0 -35
  266. package/build/types/sim/dex-conditions.d.ts +0 -518
  267. package/build/types/sim/dex-data.d.ts +0 -169
  268. package/build/types/sim/dex-formats.d.ts +0 -170
  269. package/build/types/sim/dex-items.d.ts +0 -110
  270. package/build/types/sim/dex-moves.d.ts +0 -441
  271. package/build/types/sim/dex-species.d.ts +0 -289
  272. package/build/types/sim/dex.d.ts +0 -162
  273. package/build/types/sim/exported-global-types.d.ts +0 -510
  274. package/build/types/sim/field.d.ts +0 -30
  275. package/build/types/sim/global-types.d.ts +0 -510
  276. package/build/types/sim/index.d.ts +0 -13
  277. package/build/types/sim/pokemon.d.ts +0 -427
  278. package/build/types/sim/prng.d.ts +0 -97
  279. package/build/types/sim/side.d.ts +0 -127
  280. package/build/types/sim/state.d.ts +0 -42
  281. package/build/types/sim/team-validator.d.ts +0 -198
  282. package/build/types/sim/teams.d.ts +0 -26
  283. package/build/types/sim/tools/exhaustive-runner.d.ts +0 -52
  284. package/build/types/sim/tools/index.d.ts +0 -2
  285. package/build/types/sim/tools/random-player-ai.d.ts +0 -32
  286. package/build/types/sim/tools/runner.d.ts +0 -41
@@ -37,14 +37,21 @@ exports.Abilities = void 0;
37
37
  exports.Abilities = {
38
38
  noability: {
39
39
  isNonstandard: "Past",
40
+ flags: {},
40
41
  name: "No Ability",
41
42
  rating: 0.1,
42
43
  num: 0,
43
44
  },
44
45
  adaptability: {
45
- onModifyMove(move) {
46
- move.stab = 2;
46
+ onModifySTAB(stab, source, target, move) {
47
+ if (move.forceSTAB || source.hasType(move.type)) {
48
+ if (stab === 2) {
49
+ return 2.25;
50
+ }
51
+ return 2;
52
+ }
47
53
  },
54
+ flags: {},
48
55
  name: "Adaptability",
49
56
  rating: 4,
50
57
  num: 91,
@@ -66,18 +73,20 @@ exports.Abilities = {
66
73
  if (move.typeChangerBoosted === this.effect)
67
74
  return this.chainModify([4915, 4096]);
68
75
  },
76
+ flags: {},
69
77
  name: "Aerilate",
70
78
  rating: 4,
71
79
  num: 184,
72
80
  },
73
81
  aftermath: {
74
- name: "Aftermath",
75
82
  onDamagingHitOrder: 1,
76
83
  onDamagingHit(damage, target, source, move) {
77
84
  if (!target.hp && this.checkMoveMakesContact(move, source, target, true)) {
78
85
  this.damage(source.baseMaxhp / 4, source, target);
79
86
  }
80
87
  },
88
+ flags: {},
89
+ name: "Aftermath",
81
90
  rating: 2,
82
91
  num: 106,
83
92
  },
@@ -97,6 +106,7 @@ exports.Abilities = {
97
106
  this.eachEvent('WeatherChange', this.effect);
98
107
  },
99
108
  suppressWeather: true,
109
+ flags: {},
100
110
  name: "Air Lock",
101
111
  rating: 1.5,
102
112
  num: 76,
@@ -118,6 +128,7 @@ exports.Abilities = {
118
128
  return this.chainModify([5325, 4096]);
119
129
  }
120
130
  },
131
+ flags: {},
121
132
  name: "Analytic",
122
133
  rating: 2.5,
123
134
  num: 148,
@@ -130,6 +141,7 @@ exports.Abilities = {
130
141
  this.boost({ atk: 12 }, target, target);
131
142
  }
132
143
  },
144
+ flags: {},
133
145
  name: "Anger Point",
134
146
  rating: 1,
135
147
  num: 83,
@@ -166,6 +178,7 @@ exports.Abilities = {
166
178
  this.boost({ atk: 1, spa: 1, spe: 1, def: -1, spd: -1 }, target, target);
167
179
  }
168
180
  },
181
+ flags: {},
169
182
  name: "Anger Shell",
170
183
  rating: 3,
171
184
  num: 271,
@@ -186,6 +199,7 @@ exports.Abilities = {
186
199
  }
187
200
  }
188
201
  },
202
+ flags: {},
189
203
  name: "Anticipation",
190
204
  rating: 0.5,
191
205
  num: 107,
@@ -207,6 +221,7 @@ exports.Abilities = {
207
221
  pokemon.maybeTrapped = true;
208
222
  }
209
223
  },
224
+ flags: {},
210
225
  name: "Arena Trap",
211
226
  rating: 5,
212
227
  num: 71,
@@ -224,7 +239,7 @@ exports.Abilities = {
224
239
  return false;
225
240
  }
226
241
  },
227
- isBreakable: true,
242
+ flags: { breakable: 1 },
228
243
  name: "Armor Tail",
229
244
  rating: 2.5,
230
245
  num: 296,
@@ -239,7 +254,7 @@ exports.Abilities = {
239
254
  return null;
240
255
  }
241
256
  },
242
- isBreakable: true,
257
+ flags: { breakable: 1 },
243
258
  name: "Aroma Veil",
244
259
  rating: 2,
245
260
  num: 165,
@@ -261,7 +276,7 @@ exports.Abilities = {
261
276
  this.boost({ atk: length }, source, source, this.dex.abilities.get('chillingneigh'));
262
277
  }
263
278
  },
264
- isPermanent: true,
279
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
265
280
  name: "As One (Glastrier)",
266
281
  rating: 3.5,
267
282
  num: 266,
@@ -283,7 +298,7 @@ exports.Abilities = {
283
298
  this.boost({ spa: length }, source, source, this.dex.abilities.get('grimneigh'));
284
299
  }
285
300
  },
286
- isPermanent: true,
301
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
287
302
  name: "As One (Spectrier)",
288
303
  rating: 3.5,
289
304
  num: 267,
@@ -299,7 +314,7 @@ exports.Abilities = {
299
314
  return;
300
315
  move.hasAuraBreak = true;
301
316
  },
302
- isBreakable: true,
317
+ flags: { breakable: 1 },
303
318
  name: "Aura Break",
304
319
  rating: 1,
305
320
  num: 188,
@@ -316,11 +331,13 @@ exports.Abilities = {
316
331
  }
317
332
  }
318
333
  },
334
+ flags: {},
319
335
  name: "Bad Dreams",
320
336
  rating: 1.5,
321
337
  num: 123,
322
338
  },
323
339
  ballfetch: {
340
+ flags: {},
324
341
  name: "Ball Fetch",
325
342
  rating: 0,
326
343
  num: 237,
@@ -333,13 +350,14 @@ exports.Abilities = {
333
350
  return this.chainModify([5325, 4096]);
334
351
  }
335
352
  },
353
+ flags: {},
336
354
  name: "Battery",
337
355
  rating: 0,
338
356
  num: 217,
339
357
  },
340
358
  battlearmor: {
341
359
  onCriticalHit: false,
342
- isBreakable: true,
360
+ flags: { breakable: 1 },
343
361
  name: "Battle Armor",
344
362
  rating: 1,
345
363
  num: 4,
@@ -356,7 +374,7 @@ exports.Abilities = {
356
374
  source.abilityState.battleBondTriggered = true;
357
375
  }
358
376
  },
359
- isPermanent: true,
377
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
360
378
  name: "Battle Bond",
361
379
  rating: 3.5,
362
380
  num: 210,
@@ -378,6 +396,7 @@ exports.Abilities = {
378
396
  this.debug('Beads of Ruin SpD drop');
379
397
  return this.chainModify(0.75);
380
398
  },
399
+ flags: {},
381
400
  name: "Beads of Ruin",
382
401
  rating: 4.5,
383
402
  num: 284,
@@ -389,6 +408,7 @@ exports.Abilities = {
389
408
  this.boost({ [bestStat]: length }, source);
390
409
  }
391
410
  },
411
+ flags: {},
392
412
  name: "Beast Boost",
393
413
  rating: 3.5,
394
414
  num: 224,
@@ -425,6 +445,7 @@ exports.Abilities = {
425
445
  this.boost({ spa: 1 }, target, target);
426
446
  }
427
447
  },
448
+ flags: {},
428
449
  name: "Berserk",
429
450
  rating: 2,
430
451
  num: 201,
@@ -440,7 +461,7 @@ exports.Abilities = {
440
461
  }
441
462
  }
442
463
  },
443
- isBreakable: true,
464
+ flags: { breakable: 1 },
444
465
  name: "Big Pecks",
445
466
  rating: 0.5,
446
467
  num: 145,
@@ -460,6 +481,7 @@ exports.Abilities = {
460
481
  return this.chainModify(1.5);
461
482
  }
462
483
  },
484
+ flags: {},
463
485
  name: "Blaze",
464
486
  rating: 2,
465
487
  num: 66,
@@ -471,7 +493,7 @@ exports.Abilities = {
471
493
  return null;
472
494
  }
473
495
  },
474
- isBreakable: true,
496
+ flags: { breakable: 1 },
475
497
  name: "Bulletproof",
476
498
  rating: 3,
477
499
  num: 171,
@@ -480,6 +502,7 @@ exports.Abilities = {
480
502
  onEatItem(item, pokemon) {
481
503
  this.heal(pokemon.baseMaxhp / 3);
482
504
  },
505
+ flags: {},
483
506
  name: "Cheek Pouch",
484
507
  rating: 2,
485
508
  num: 167,
@@ -490,6 +513,7 @@ exports.Abilities = {
490
513
  this.boost({ atk: length }, source);
491
514
  }
492
515
  },
516
+ flags: {},
493
517
  name: "Chilling Neigh",
494
518
  rating: 3,
495
519
  num: 264,
@@ -500,6 +524,7 @@ exports.Abilities = {
500
524
  return this.chainModify(2);
501
525
  }
502
526
  },
527
+ flags: {},
503
528
  name: "Chlorophyll",
504
529
  rating: 3,
505
530
  num: 34,
@@ -520,7 +545,7 @@ exports.Abilities = {
520
545
  this.add("-fail", target, "unboost", "[from] ability: Clear Body", "[of] " + target);
521
546
  }
522
547
  },
523
- isBreakable: true,
548
+ flags: { breakable: 1 },
524
549
  name: "Clear Body",
525
550
  rating: 2,
526
551
  num: 29,
@@ -541,6 +566,7 @@ exports.Abilities = {
541
566
  this.eachEvent('WeatherChange', this.effect);
542
567
  },
543
568
  suppressWeather: true,
569
+ flags: {},
544
570
  name: "Cloud Nine",
545
571
  rating: 1.5,
546
572
  num: 13,
@@ -564,6 +590,7 @@ exports.Abilities = {
564
590
  }
565
591
  }
566
592
  },
593
+ flags: {},
567
594
  name: "Color Change",
568
595
  rating: 0,
569
596
  num: 16,
@@ -579,7 +606,7 @@ exports.Abilities = {
579
606
  return false;
580
607
  },
581
608
  // Permanent sleep "status" implemented in the relevant sleep-checking effects
582
- isPermanent: true,
609
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
583
610
  name: "Comatose",
584
611
  rating: 4,
585
612
  num: 213,
@@ -589,8 +616,7 @@ exports.Abilities = {
589
616
  if (this.gameType !== 'doubles')
590
617
  return;
591
618
  const ally = pokemon.allies()[0];
592
- if (!ally || pokemon.transformed ||
593
- pokemon.baseSpecies.baseSpecies !== 'Tatsugiri' || ally.baseSpecies.baseSpecies !== 'Dondozo') {
619
+ if (!ally || pokemon.baseSpecies.baseSpecies !== 'Tatsugiri' || ally.baseSpecies.baseSpecies !== 'Dondozo') {
594
620
  // Handle any edge cases
595
621
  if (pokemon.getVolatile('commanding'))
596
622
  pokemon.removeVolatile('commanding');
@@ -614,6 +640,7 @@ exports.Abilities = {
614
640
  pokemon.removeVolatile('commanding');
615
641
  }
616
642
  },
643
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1 },
617
644
  name: "Commander",
618
645
  rating: 0,
619
646
  num: 279,
@@ -637,6 +664,7 @@ exports.Abilities = {
637
664
  this.boost({ spa: 2 }, target, target, null, false, true);
638
665
  }
639
666
  },
667
+ flags: {},
640
668
  name: "Competitive",
641
669
  rating: 2.5,
642
670
  num: 172,
@@ -649,6 +677,7 @@ exports.Abilities = {
649
677
  this.debug('compoundeyes - enhancing accuracy');
650
678
  return this.chainModify([5325, 4096]);
651
679
  },
680
+ flags: {},
652
681
  name: "Compound Eyes",
653
682
  rating: 3,
654
683
  num: 14,
@@ -662,13 +691,14 @@ exports.Abilities = {
662
691
  boost[i] *= -1;
663
692
  }
664
693
  },
665
- isBreakable: true,
694
+ flags: { breakable: 1 },
666
695
  name: "Contrary",
667
696
  rating: 4.5,
668
697
  num: 126,
669
698
  },
670
699
  corrosion: {
671
700
  // Implemented in sim/pokemon.js:Pokemon#setStatus
701
+ flags: {},
672
702
  name: "Corrosion",
673
703
  rating: 2.5,
674
704
  num: 212,
@@ -695,6 +725,7 @@ exports.Abilities = {
695
725
  }
696
726
  this.add('-copyboost', pokemon, ally, '[from] ability: Costar');
697
727
  },
728
+ flags: {},
698
729
  name: "Costar",
699
730
  rating: 0,
700
731
  num: 294,
@@ -712,6 +743,7 @@ exports.Abilities = {
712
743
  this.boost({ spe: -1 }, pokemon, target, null, true);
713
744
  }
714
745
  },
746
+ flags: {},
715
747
  name: "Cotton Down",
716
748
  rating: 2,
717
749
  num: 238,
@@ -746,6 +778,7 @@ exports.Abilities = {
746
778
  }
747
779
  },
748
780
  },
781
+ flags: {},
749
782
  name: "Cud Chew",
750
783
  rating: 2,
751
784
  num: 291,
@@ -757,6 +790,7 @@ exports.Abilities = {
757
790
  this.add('-clearboost', ally, '[from] ability: Curious Medicine', '[of] ' + pokemon);
758
791
  }
759
792
  },
793
+ flags: {},
760
794
  name: "Curious Medicine",
761
795
  rating: 0,
762
796
  num: 261,
@@ -771,6 +805,7 @@ exports.Abilities = {
771
805
  }
772
806
  }
773
807
  },
808
+ flags: {},
774
809
  name: "Cursed Body",
775
810
  rating: 2,
776
811
  num: 130,
@@ -783,6 +818,7 @@ exports.Abilities = {
783
818
  }
784
819
  }
785
820
  },
821
+ flags: {},
786
822
  name: "Cute Charm",
787
823
  rating: 0.5,
788
824
  num: 56,
@@ -800,12 +836,13 @@ exports.Abilities = {
800
836
  return false;
801
837
  }
802
838
  },
803
- isBreakable: true,
839
+ flags: { breakable: 1 },
804
840
  name: "Damp",
805
841
  rating: 0.5,
806
842
  num: 6,
807
843
  },
808
844
  dancer: {
845
+ flags: {},
809
846
  name: "Dancer",
810
847
  // implemented in runMove in scripts.js
811
848
  rating: 1.5,
@@ -827,6 +864,7 @@ exports.Abilities = {
827
864
  return;
828
865
  return this.chainModify([move.hasAuraBreak ? 3072 : 5448, 4096]);
829
866
  },
867
+ flags: {},
830
868
  name: "Dark Aura",
831
869
  rating: 3,
832
870
  num: 186,
@@ -838,6 +876,7 @@ exports.Abilities = {
838
876
  pokemon.shieldBoost = true;
839
877
  this.boost({ def: 1 }, pokemon);
840
878
  },
879
+ flags: {},
841
880
  name: "Dauntless Shield",
842
881
  rating: 3.5,
843
882
  num: 235,
@@ -855,7 +894,7 @@ exports.Abilities = {
855
894
  return false;
856
895
  }
857
896
  },
858
- isBreakable: true,
897
+ flags: { breakable: 1 },
859
898
  name: "Dazzling",
860
899
  rating: 2.5,
861
900
  num: 219,
@@ -873,6 +912,7 @@ exports.Abilities = {
873
912
  return this.chainModify(0.5);
874
913
  }
875
914
  },
915
+ flags: {},
876
916
  name: "Defeatist",
877
917
  rating: -1,
878
918
  num: 129,
@@ -896,6 +936,7 @@ exports.Abilities = {
896
936
  this.boost({ atk: 2 }, target, target, null, false, true);
897
937
  }
898
938
  },
939
+ flags: {},
899
940
  name: "Defiant",
900
941
  rating: 3,
901
942
  num: 128,
@@ -922,6 +963,7 @@ exports.Abilities = {
922
963
  }
923
964
  this.field.clearWeather();
924
965
  },
966
+ flags: {},
925
967
  name: "Delta Stream",
926
968
  rating: 4,
927
969
  num: 191,
@@ -948,6 +990,7 @@ exports.Abilities = {
948
990
  }
949
991
  this.field.clearWeather();
950
992
  },
993
+ flags: {},
951
994
  name: "Desolate Land",
952
995
  rating: 4.5,
953
996
  num: 190,
@@ -955,8 +998,7 @@ exports.Abilities = {
955
998
  disguise: {
956
999
  onDamagePriority: 1,
957
1000
  onDamage(damage, target, source, effect) {
958
- if (effect && effect.effectType === 'Move' &&
959
- ['mimikyu', 'mimikyutotem'].includes(target.species.id) && !target.transformed) {
1001
+ if (effect?.effectType === 'Move' && ['mimikyu', 'mimikyutotem'].includes(target.species.id)) {
960
1002
  this.add('-activate', target, 'ability: Disguise');
961
1003
  this.effectState.busted = true;
962
1004
  return 0;
@@ -965,7 +1007,7 @@ exports.Abilities = {
965
1007
  onCriticalHit(target, source, move) {
966
1008
  if (!target)
967
1009
  return;
968
- if (!['mimikyu', 'mimikyutotem'].includes(target.species.id) || target.transformed) {
1010
+ if (!['mimikyu', 'mimikyutotem'].includes(target.species.id)) {
969
1011
  return;
970
1012
  }
971
1013
  const hitSub = target.volatiles['substitute'] && !move.flags['bypasssub'] && !(move.infiltrates && this.gen >= 6);
@@ -978,7 +1020,7 @@ exports.Abilities = {
978
1020
  onEffectiveness(typeMod, target, type, move) {
979
1021
  if (!target || move.category === 'Status')
980
1022
  return;
981
- if (!['mimikyu', 'mimikyutotem'].includes(target.species.id) || target.transformed) {
1023
+ if (!['mimikyu', 'mimikyutotem'].includes(target.species.id)) {
982
1024
  return;
983
1025
  }
984
1026
  const hitSub = target.volatiles['substitute'] && !move.flags['bypasssub'] && !(move.infiltrates && this.gen >= 6);
@@ -995,8 +1037,10 @@ exports.Abilities = {
995
1037
  this.damage(pokemon.baseMaxhp / 8, pokemon, pokemon, this.dex.species.get(speciesid));
996
1038
  }
997
1039
  },
998
- isBreakable: true,
999
- isPermanent: true,
1040
+ flags: {
1041
+ failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1,
1042
+ breakable: 1, notransform: 1,
1043
+ },
1000
1044
  name: "Disguise",
1001
1045
  rating: 3.5,
1002
1046
  num: 209,
@@ -1016,6 +1060,7 @@ exports.Abilities = {
1016
1060
  this.boost({ atk: 1 });
1017
1061
  }
1018
1062
  },
1063
+ flags: {},
1019
1064
  name: "Download",
1020
1065
  rating: 3.5,
1021
1066
  num: 88,
@@ -1035,6 +1080,7 @@ exports.Abilities = {
1035
1080
  return this.chainModify(1.5);
1036
1081
  }
1037
1082
  },
1083
+ flags: {},
1038
1084
  name: "Dragon's Maw",
1039
1085
  rating: 3.5,
1040
1086
  num: 263,
@@ -1049,6 +1095,7 @@ exports.Abilities = {
1049
1095
  }
1050
1096
  this.field.setWeather('raindance');
1051
1097
  },
1098
+ flags: {},
1052
1099
  name: "Drizzle",
1053
1100
  rating: 4,
1054
1101
  num: 2,
@@ -1063,6 +1110,7 @@ exports.Abilities = {
1063
1110
  }
1064
1111
  this.field.setWeather('sunnyday');
1065
1112
  },
1113
+ flags: {},
1066
1114
  name: "Drought",
1067
1115
  rating: 4,
1068
1116
  num: 70,
@@ -1092,12 +1140,13 @@ exports.Abilities = {
1092
1140
  this.damage(target.baseMaxhp / 8, target, target);
1093
1141
  }
1094
1142
  },
1095
- isBreakable: true,
1143
+ flags: { breakable: 1 },
1096
1144
  name: "Dry Skin",
1097
1145
  rating: 3,
1098
1146
  num: 87,
1099
1147
  },
1100
1148
  earlybird: {
1149
+ flags: {},
1101
1150
  name: "Early Bird",
1102
1151
  // Implemented in statuses.js
1103
1152
  rating: 1.5,
@@ -1112,7 +1161,7 @@ exports.Abilities = {
1112
1161
  return null;
1113
1162
  }
1114
1163
  },
1115
- isBreakable: true,
1164
+ flags: { breakable: 1 },
1116
1165
  name: "Earth Eater",
1117
1166
  rating: 3.5,
1118
1167
  num: 297,
@@ -1132,6 +1181,7 @@ exports.Abilities = {
1132
1181
  }
1133
1182
  }
1134
1183
  },
1184
+ flags: {},
1135
1185
  name: "Effect Spore",
1136
1186
  rating: 2,
1137
1187
  num: 27,
@@ -1140,6 +1190,7 @@ exports.Abilities = {
1140
1190
  onStart(source) {
1141
1191
  this.field.setTerrain('electricterrain');
1142
1192
  },
1193
+ flags: {},
1143
1194
  name: "Electric Surge",
1144
1195
  rating: 4,
1145
1196
  num: 226,
@@ -1149,13 +1200,14 @@ exports.Abilities = {
1149
1200
  onDamagingHit(damage, target, source, move) {
1150
1201
  target.addVolatile('charge');
1151
1202
  },
1203
+ flags: {},
1152
1204
  name: "Electromorphosis",
1153
1205
  rating: 3,
1154
1206
  num: 280,
1155
1207
  },
1156
1208
  embodyaspectcornerstone: {
1157
1209
  onStart(pokemon) {
1158
- if (pokemon.baseSpecies.name === 'Ogerpon-Cornerstone-Tera' && !pokemon.transformed && !this.effectState.embodied) {
1210
+ if (pokemon.baseSpecies.name === 'Ogerpon-Cornerstone-Tera' && !this.effectState.embodied) {
1159
1211
  this.effectState.embodied = true;
1160
1212
  this.boost({ def: 1 }, pokemon);
1161
1213
  }
@@ -1163,13 +1215,14 @@ exports.Abilities = {
1163
1215
  onSwitchIn() {
1164
1216
  delete this.effectState.embodied;
1165
1217
  },
1218
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
1166
1219
  name: "Embody Aspect (Cornerstone)",
1167
1220
  rating: 3.5,
1168
1221
  num: 304,
1169
1222
  },
1170
1223
  embodyaspecthearthflame: {
1171
1224
  onStart(pokemon) {
1172
- if (pokemon.baseSpecies.name === 'Ogerpon-Hearthflame-Tera' && !pokemon.transformed && !this.effectState.embodied) {
1225
+ if (pokemon.baseSpecies.name === 'Ogerpon-Hearthflame-Tera' && !this.effectState.embodied) {
1173
1226
  this.effectState.embodied = true;
1174
1227
  this.boost({ atk: 1 }, pokemon);
1175
1228
  }
@@ -1177,13 +1230,14 @@ exports.Abilities = {
1177
1230
  onSwitchIn() {
1178
1231
  delete this.effectState.embodied;
1179
1232
  },
1233
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
1180
1234
  name: "Embody Aspect (Hearthflame)",
1181
1235
  rating: 3.5,
1182
1236
  num: 303,
1183
1237
  },
1184
1238
  embodyaspectteal: {
1185
1239
  onStart(pokemon) {
1186
- if (pokemon.baseSpecies.name === 'Ogerpon-Teal-Tera' && !pokemon.transformed && !this.effectState.embodied) {
1240
+ if (pokemon.baseSpecies.name === 'Ogerpon-Teal-Tera' && !this.effectState.embodied) {
1187
1241
  this.effectState.embodied = true;
1188
1242
  this.boost({ spe: 1 }, pokemon);
1189
1243
  }
@@ -1191,13 +1245,14 @@ exports.Abilities = {
1191
1245
  onSwitchIn() {
1192
1246
  delete this.effectState.embodied;
1193
1247
  },
1248
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
1194
1249
  name: "Embody Aspect (Teal)",
1195
1250
  rating: 3.5,
1196
1251
  num: 301,
1197
1252
  },
1198
1253
  embodyaspectwellspring: {
1199
1254
  onStart(pokemon) {
1200
- if (pokemon.baseSpecies.name === 'Ogerpon-Wellspring-Tera' && !pokemon.transformed && !this.effectState.embodied) {
1255
+ if (pokemon.baseSpecies.name === 'Ogerpon-Wellspring-Tera' && !this.effectState.embodied) {
1201
1256
  this.effectState.embodied = true;
1202
1257
  this.boost({ spd: 1 }, pokemon);
1203
1258
  }
@@ -1205,6 +1260,7 @@ exports.Abilities = {
1205
1260
  onSwitchIn() {
1206
1261
  delete this.effectState.embodied;
1207
1262
  },
1263
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
1208
1264
  name: "Embody Aspect (Wellspring)",
1209
1265
  rating: 3.5,
1210
1266
  num: 302,
@@ -1221,6 +1277,7 @@ exports.Abilities = {
1221
1277
  target.switchFlag = true;
1222
1278
  this.add('-activate', target, 'ability: Emergency Exit');
1223
1279
  },
1280
+ flags: {},
1224
1281
  name: "Emergency Exit",
1225
1282
  rating: 1,
1226
1283
  num: 194,
@@ -1241,6 +1298,7 @@ exports.Abilities = {
1241
1298
  return;
1242
1299
  return this.chainModify([move.hasAuraBreak ? 3072 : 5448, 4096]);
1243
1300
  },
1301
+ flags: {},
1244
1302
  name: "Fairy Aura",
1245
1303
  rating: 3,
1246
1304
  num: 187,
@@ -1252,7 +1310,7 @@ exports.Abilities = {
1252
1310
  return this.chainModify(0.75);
1253
1311
  }
1254
1312
  },
1255
- isBreakable: true,
1313
+ flags: { breakable: 1 },
1256
1314
  name: "Filter",
1257
1315
  rating: 3,
1258
1316
  num: 111,
@@ -1265,6 +1323,7 @@ exports.Abilities = {
1265
1323
  }
1266
1324
  }
1267
1325
  },
1326
+ flags: {},
1268
1327
  name: "Flame Body",
1269
1328
  rating: 2,
1270
1329
  num: 49,
@@ -1276,6 +1335,7 @@ exports.Abilities = {
1276
1335
  return this.chainModify(1.5);
1277
1336
  }
1278
1337
  },
1338
+ flags: {},
1279
1339
  name: "Flare Boost",
1280
1340
  rating: 2,
1281
1341
  num: 138,
@@ -1316,7 +1376,7 @@ exports.Abilities = {
1316
1376
  this.add('-end', target, 'ability: Flash Fire', '[silent]');
1317
1377
  },
1318
1378
  },
1319
- isBreakable: true,
1379
+ flags: { breakable: 1 },
1320
1380
  name: "Flash Fire",
1321
1381
  rating: 3.5,
1322
1382
  num: 18,
@@ -1357,7 +1417,7 @@ exports.Abilities = {
1357
1417
  return this.chainModify(1.5);
1358
1418
  }
1359
1419
  },
1360
- isBreakable: true,
1420
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, breakable: 1 },
1361
1421
  name: "Flower Gift",
1362
1422
  rating: 1,
1363
1423
  num: 122,
@@ -1397,7 +1457,7 @@ exports.Abilities = {
1397
1457
  return null;
1398
1458
  }
1399
1459
  },
1400
- isBreakable: true,
1460
+ flags: { breakable: 1 },
1401
1461
  name: "Flower Veil",
1402
1462
  rating: 0,
1403
1463
  num: 166,
@@ -1411,7 +1471,7 @@ exports.Abilities = {
1411
1471
  mod /= 2;
1412
1472
  return this.chainModify(mod);
1413
1473
  },
1414
- isBreakable: true,
1474
+ flags: { breakable: 1 },
1415
1475
  name: "Fluffy",
1416
1476
  rating: 3.5,
1417
1477
  num: 218,
@@ -1449,6 +1509,7 @@ exports.Abilities = {
1449
1509
  pokemon.formeChange(forme, this.effect, false, '[msg]');
1450
1510
  }
1451
1511
  },
1512
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1 },
1452
1513
  name: "Forecast",
1453
1514
  rating: 2,
1454
1515
  num: 59,
@@ -1483,19 +1544,20 @@ exports.Abilities = {
1483
1544
  const [warnMoveName, warnTarget] = this.sample(warnMoves);
1484
1545
  this.add('-activate', pokemon, 'ability: Forewarn', warnMoveName, '[of] ' + warnTarget);
1485
1546
  },
1547
+ flags: {},
1486
1548
  name: "Forewarn",
1487
1549
  rating: 0.5,
1488
1550
  num: 108,
1489
1551
  },
1490
1552
  friendguard: {
1491
- name: "Friend Guard",
1492
1553
  onAnyModifyDamage(damage, source, target, move) {
1493
1554
  if (target !== this.effectState.target && target.isAlly(this.effectState.target)) {
1494
1555
  this.debug('Friend Guard weaken');
1495
1556
  return this.chainModify(0.75);
1496
1557
  }
1497
1558
  },
1498
- isBreakable: true,
1559
+ flags: { breakable: 1 },
1560
+ name: "Friend Guard",
1499
1561
  rating: 0,
1500
1562
  num: 132,
1501
1563
  },
@@ -1507,6 +1569,7 @@ exports.Abilities = {
1507
1569
  }
1508
1570
  }
1509
1571
  },
1572
+ flags: {},
1510
1573
  name: "Frisk",
1511
1574
  rating: 1.5,
1512
1575
  num: 119,
@@ -1527,6 +1590,7 @@ exports.Abilities = {
1527
1590
  this.add("-fail", target, "unboost", "[from] ability: Full Metal Body", "[of] " + target);
1528
1591
  }
1529
1592
  },
1593
+ flags: {},
1530
1594
  name: "Full Metal Body",
1531
1595
  rating: 2,
1532
1596
  num: 230,
@@ -1536,7 +1600,7 @@ exports.Abilities = {
1536
1600
  onModifyDef(def) {
1537
1601
  return this.chainModify(2);
1538
1602
  },
1539
- isBreakable: true,
1603
+ flags: { breakable: 1 },
1540
1604
  name: "Fur Coat",
1541
1605
  rating: 4,
1542
1606
  num: 169,
@@ -1546,6 +1610,7 @@ exports.Abilities = {
1546
1610
  if (move?.type === 'Flying' && pokemon.hp === pokemon.maxhp)
1547
1611
  return priority + 1;
1548
1612
  },
1613
+ flags: {},
1549
1614
  name: "Gale Wings",
1550
1615
  rating: 1.5,
1551
1616
  num: 177,
@@ -1567,20 +1632,22 @@ exports.Abilities = {
1567
1632
  if (move.typeChangerBoosted === this.effect)
1568
1633
  return this.chainModify([4915, 4096]);
1569
1634
  },
1635
+ flags: {},
1570
1636
  name: "Galvanize",
1571
1637
  rating: 4,
1572
1638
  num: 206,
1573
1639
  },
1574
1640
  gluttony: {
1575
- name: "Gluttony",
1576
- rating: 1.5,
1577
- num: 82,
1578
1641
  onStart(pokemon) {
1579
1642
  pokemon.abilityState.gluttony = true;
1580
1643
  },
1581
1644
  onDamage(item, pokemon) {
1582
1645
  pokemon.abilityState.gluttony = true;
1583
1646
  },
1647
+ flags: {},
1648
+ name: "Gluttony",
1649
+ rating: 1.5,
1650
+ num: 82,
1584
1651
  },
1585
1652
  goodasgold: {
1586
1653
  onTryHit(target, source, move) {
@@ -1589,7 +1656,7 @@ exports.Abilities = {
1589
1656
  return null;
1590
1657
  }
1591
1658
  },
1592
- isBreakable: true,
1659
+ flags: { breakable: 1 },
1593
1660
  name: "Good as Gold",
1594
1661
  rating: 5,
1595
1662
  num: 283,
@@ -1601,6 +1668,7 @@ exports.Abilities = {
1601
1668
  this.boost({ spe: -1 }, source, target, null, true);
1602
1669
  }
1603
1670
  },
1671
+ flags: {},
1604
1672
  name: "Gooey",
1605
1673
  rating: 2,
1606
1674
  num: 183,
@@ -1648,6 +1716,7 @@ exports.Abilities = {
1648
1716
  onEnd(pokemon) {
1649
1717
  pokemon.abilityState.choiceLock = "";
1650
1718
  },
1719
+ flags: {},
1651
1720
  name: "Gorilla Tactics",
1652
1721
  rating: 4.5,
1653
1722
  num: 255,
@@ -1658,7 +1727,7 @@ exports.Abilities = {
1658
1727
  if (this.field.isTerrain('grassyterrain'))
1659
1728
  return this.chainModify(1.5);
1660
1729
  },
1661
- isBreakable: true,
1730
+ flags: { breakable: 1 },
1662
1731
  name: "Grass Pelt",
1663
1732
  rating: 0.5,
1664
1733
  num: 179,
@@ -1667,6 +1736,7 @@ exports.Abilities = {
1667
1736
  onStart(source) {
1668
1737
  this.field.setTerrain('grassyterrain');
1669
1738
  },
1739
+ flags: {},
1670
1740
  name: "Grassy Surge",
1671
1741
  rating: 4,
1672
1742
  num: 229,
@@ -1677,6 +1747,7 @@ exports.Abilities = {
1677
1747
  this.boost({ spa: length }, source);
1678
1748
  }
1679
1749
  },
1750
+ flags: {},
1680
1751
  name: "Grim Neigh",
1681
1752
  rating: 3,
1682
1753
  num: 265,
@@ -1693,14 +1764,14 @@ exports.Abilities = {
1693
1764
  this.boost({ atk: 1 }, target, target, null, false, true);
1694
1765
  }
1695
1766
  },
1696
- isBreakable: true,
1767
+ flags: { breakable: 1 },
1697
1768
  name: "Guard Dog",
1698
1769
  rating: 2,
1699
1770
  num: 275,
1700
1771
  },
1701
1772
  gulpmissile: {
1702
1773
  onDamagingHit(damage, target, source, move) {
1703
- if (!source.hp || !source.isActive || target.transformed || target.isSemiInvulnerable())
1774
+ if (!source.hp || !source.isActive || target.isSemiInvulnerable())
1704
1775
  return;
1705
1776
  if (['cramorantgulping', 'cramorantgorging'].includes(target.species.id)) {
1706
1777
  this.damage(source.baseMaxhp / 4, source, target);
@@ -1715,13 +1786,12 @@ exports.Abilities = {
1715
1786
  },
1716
1787
  // The Dive part of this mechanic is implemented in Dive's `onTryMove` in moves.ts
1717
1788
  onSourceTryPrimaryHit(target, source, effect) {
1718
- if (effect && effect.id === 'surf' && source.hasAbility('gulpmissile') &&
1719
- source.species.name === 'Cramorant' && !source.transformed) {
1789
+ if (effect?.id === 'surf' && source.hasAbility('gulpmissile') && source.species.name === 'Cramorant') {
1720
1790
  const forme = source.hp <= source.maxhp / 2 ? 'cramorantgorging' : 'cramorantgulping';
1721
1791
  source.formeChange(forme, effect);
1722
1792
  }
1723
1793
  },
1724
- isPermanent: true,
1794
+ flags: { cantsuppress: 1, notransform: 1 },
1725
1795
  name: "Gulp Missile",
1726
1796
  rating: 2.5,
1727
1797
  num: 241,
@@ -1733,6 +1803,7 @@ exports.Abilities = {
1733
1803
  return this.chainModify(1.5);
1734
1804
  }
1735
1805
  },
1806
+ flags: {},
1736
1807
  name: "Guts",
1737
1808
  rating: 3.5,
1738
1809
  num: 62,
@@ -1750,12 +1821,12 @@ exports.Abilities = {
1750
1821
  return this.chainModify([5461, 4096]);
1751
1822
  }
1752
1823
  },
1824
+ flags: {},
1753
1825
  name: "Hadron Engine",
1754
1826
  rating: 4.5,
1755
1827
  num: 289,
1756
1828
  },
1757
1829
  harvest: {
1758
- name: "Harvest",
1759
1830
  onResidualOrder: 28,
1760
1831
  onResidualSubOrder: 2,
1761
1832
  onResidual(pokemon) {
@@ -1767,11 +1838,12 @@ exports.Abilities = {
1767
1838
  }
1768
1839
  }
1769
1840
  },
1841
+ flags: {},
1842
+ name: "Harvest",
1770
1843
  rating: 2.5,
1771
1844
  num: 139,
1772
1845
  },
1773
1846
  healer: {
1774
- name: "Healer",
1775
1847
  onResidualOrder: 5,
1776
1848
  onResidualSubOrder: 3,
1777
1849
  onResidual(pokemon) {
@@ -1782,6 +1854,8 @@ exports.Abilities = {
1782
1854
  }
1783
1855
  }
1784
1856
  },
1857
+ flags: {},
1858
+ name: "Healer",
1785
1859
  rating: 0,
1786
1860
  num: 131,
1787
1861
  },
@@ -1805,7 +1879,7 @@ exports.Abilities = {
1805
1879
  return damage / 2;
1806
1880
  }
1807
1881
  },
1808
- isBreakable: true,
1882
+ flags: { breakable: 1 },
1809
1883
  name: "Heatproof",
1810
1884
  rating: 2,
1811
1885
  num: 85,
@@ -1815,12 +1889,13 @@ exports.Abilities = {
1815
1889
  onModifyWeight(weighthg) {
1816
1890
  return weighthg * 2;
1817
1891
  },
1818
- isBreakable: true,
1892
+ flags: { breakable: 1 },
1819
1893
  name: "Heavy Metal",
1820
1894
  rating: 0,
1821
1895
  num: 134,
1822
1896
  },
1823
1897
  honeygather: {
1898
+ flags: {},
1824
1899
  name: "Honey Gather",
1825
1900
  rating: 0,
1826
1901
  num: 118,
@@ -1831,6 +1906,7 @@ exports.Abilities = {
1831
1906
  this.heal(ally.baseMaxhp / 4, ally, pokemon);
1832
1907
  }
1833
1908
  },
1909
+ flags: {},
1834
1910
  name: "Hospitality",
1835
1911
  rating: 0,
1836
1912
  num: 299,
@@ -1840,6 +1916,7 @@ exports.Abilities = {
1840
1916
  onModifyAtk(atk) {
1841
1917
  return this.chainModify(2);
1842
1918
  },
1919
+ flags: {},
1843
1920
  name: "Huge Power",
1844
1921
  rating: 5,
1845
1922
  num: 37,
@@ -1847,11 +1924,12 @@ exports.Abilities = {
1847
1924
  hungerswitch: {
1848
1925
  onResidualOrder: 29,
1849
1926
  onResidual(pokemon) {
1850
- if (pokemon.species.baseSpecies !== 'Morpeko' || pokemon.transformed || pokemon.terastallized)
1927
+ if (pokemon.species.baseSpecies !== 'Morpeko' || pokemon.terastallized)
1851
1928
  return;
1852
1929
  const targetForme = pokemon.species.name === 'Morpeko' ? 'Morpeko-Hangry' : 'Morpeko';
1853
1930
  pokemon.formeChange(targetForme);
1854
1931
  },
1932
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
1855
1933
  name: "Hunger Switch",
1856
1934
  rating: 1,
1857
1935
  num: 258,
@@ -1868,6 +1946,7 @@ exports.Abilities = {
1868
1946
  return this.chainModify([3277, 4096]);
1869
1947
  }
1870
1948
  },
1949
+ flags: {},
1871
1950
  name: "Hustle",
1872
1951
  rating: 3.5,
1873
1952
  num: 55,
@@ -1882,6 +1961,7 @@ exports.Abilities = {
1882
1961
  pokemon.cureStatus();
1883
1962
  }
1884
1963
  },
1964
+ flags: {},
1885
1965
  name: "Hydration",
1886
1966
  rating: 1.5,
1887
1967
  num: 93,
@@ -1897,7 +1977,7 @@ exports.Abilities = {
1897
1977
  }
1898
1978
  }
1899
1979
  },
1900
- isBreakable: true,
1980
+ flags: { breakable: 1 },
1901
1981
  name: "Hyper Cutter",
1902
1982
  rating: 1.5,
1903
1983
  num: 52,
@@ -1912,14 +1992,14 @@ exports.Abilities = {
1912
1992
  if (type === 'hail')
1913
1993
  return false;
1914
1994
  },
1995
+ flags: {},
1915
1996
  name: "Ice Body",
1916
1997
  rating: 1,
1917
1998
  num: 115,
1918
1999
  },
1919
2000
  iceface: {
1920
2001
  onStart(pokemon) {
1921
- if (this.field.isWeather(['hail', 'snow']) &&
1922
- pokemon.species.id === 'eiscuenoice' && !pokemon.transformed) {
2002
+ if (this.field.isWeather(['hail', 'snow']) && pokemon.species.id === 'eiscuenoice') {
1923
2003
  this.add('-activate', pokemon, 'ability: Ice Face');
1924
2004
  this.effectState.busted = false;
1925
2005
  pokemon.formeChange('Eiscue', this.effect, true);
@@ -1927,8 +2007,7 @@ exports.Abilities = {
1927
2007
  },
1928
2008
  onDamagePriority: 1,
1929
2009
  onDamage(damage, target, source, effect) {
1930
- if (effect && effect.effectType === 'Move' && effect.category === 'Physical' &&
1931
- target.species.id === 'eiscue' && !target.transformed) {
2010
+ if (effect?.effectType === 'Move' && effect.category === 'Physical' && target.species.id === 'eiscue') {
1932
2011
  this.add('-activate', target, 'ability: Ice Face');
1933
2012
  this.effectState.busted = true;
1934
2013
  return 0;
@@ -1937,7 +2016,7 @@ exports.Abilities = {
1937
2016
  onCriticalHit(target, type, move) {
1938
2017
  if (!target)
1939
2018
  return;
1940
- if (move.category !== 'Physical' || target.species.id !== 'eiscue' || target.transformed)
2019
+ if (move.category !== 'Physical' || target.species.id !== 'eiscue')
1941
2020
  return;
1942
2021
  if (target.volatiles['substitute'] && !(move.flags['bypasssub'] || move.infiltrates))
1943
2022
  return;
@@ -1948,7 +2027,7 @@ exports.Abilities = {
1948
2027
  onEffectiveness(typeMod, target, type, move) {
1949
2028
  if (!target)
1950
2029
  return;
1951
- if (move.category !== 'Physical' || target.species.id !== 'eiscue' || target.transformed)
2030
+ if (move.category !== 'Physical' || target.species.id !== 'eiscue')
1952
2031
  return;
1953
2032
  const hitSub = target.volatiles['substitute'] && !move.flags['bypasssub'] && !(move.infiltrates && this.gen >= 6);
1954
2033
  if (hitSub)
@@ -1968,15 +2047,16 @@ exports.Abilities = {
1968
2047
  return;
1969
2048
  if (!pokemon.hp)
1970
2049
  return;
1971
- if (this.field.isWeather(['hail', 'snow']) &&
1972
- pokemon.species.id === 'eiscuenoice' && !pokemon.transformed) {
2050
+ if (this.field.isWeather(['hail', 'snow']) && pokemon.species.id === 'eiscuenoice') {
1973
2051
  this.add('-activate', pokemon, 'ability: Ice Face');
1974
2052
  this.effectState.busted = false;
1975
2053
  pokemon.formeChange('Eiscue', this.effect, true);
1976
2054
  }
1977
2055
  },
1978
- isBreakable: true,
1979
- isPermanent: true,
2056
+ flags: {
2057
+ failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1,
2058
+ breakable: 1, notransform: 1,
2059
+ },
1980
2060
  name: "Ice Face",
1981
2061
  rating: 3,
1982
2062
  num: 248,
@@ -1987,7 +2067,7 @@ exports.Abilities = {
1987
2067
  return this.chainModify(0.5);
1988
2068
  }
1989
2069
  },
1990
- isBreakable: true,
2070
+ flags: { breakable: 1 },
1991
2071
  name: "Ice Scales",
1992
2072
  rating: 4,
1993
2073
  num: 246,
@@ -2006,7 +2086,7 @@ exports.Abilities = {
2006
2086
  onModifyMove(move) {
2007
2087
  move.ignoreEvasion = true;
2008
2088
  },
2009
- isBreakable: true,
2089
+ flags: { breakable: 1 },
2010
2090
  name: "Illuminate",
2011
2091
  rating: 0.5,
2012
2092
  num: 35,
@@ -2048,6 +2128,7 @@ exports.Abilities = {
2048
2128
  onFaint(pokemon) {
2049
2129
  pokemon.illusion = null;
2050
2130
  },
2131
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1 },
2051
2132
  name: "Illusion",
2052
2133
  rating: 4.5,
2053
2134
  num: 149,
@@ -2067,7 +2148,7 @@ exports.Abilities = {
2067
2148
  }
2068
2149
  return false;
2069
2150
  },
2070
- isBreakable: true,
2151
+ flags: { breakable: 1 },
2071
2152
  name: "Immunity",
2072
2153
  rating: 2,
2073
2154
  num: 17,
@@ -2089,6 +2170,7 @@ exports.Abilities = {
2089
2170
  }
2090
2171
  this.effectState.switchingIn = false;
2091
2172
  },
2173
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1 },
2092
2174
  name: "Imposter",
2093
2175
  rating: 5,
2094
2176
  num: 150,
@@ -2097,18 +2179,20 @@ exports.Abilities = {
2097
2179
  onModifyMove(move) {
2098
2180
  move.infiltrates = true;
2099
2181
  },
2182
+ flags: {},
2100
2183
  name: "Infiltrator",
2101
2184
  rating: 2.5,
2102
2185
  num: 151,
2103
2186
  },
2104
2187
  innardsout: {
2105
- name: "Innards Out",
2106
2188
  onDamagingHitOrder: 1,
2107
2189
  onDamagingHit(damage, target, source, move) {
2108
2190
  if (!target.hp) {
2109
2191
  this.damage(target.getUndynamaxedHP(damage), source, target);
2110
2192
  }
2111
2193
  },
2194
+ flags: {},
2195
+ name: "Innards Out",
2112
2196
  rating: 4,
2113
2197
  num: 215,
2114
2198
  },
@@ -2123,7 +2207,7 @@ exports.Abilities = {
2123
2207
  this.add('-fail', target, 'unboost', 'Attack', '[from] ability: Inner Focus', '[of] ' + target);
2124
2208
  }
2125
2209
  },
2126
- isBreakable: true,
2210
+ flags: { breakable: 1 },
2127
2211
  name: "Inner Focus",
2128
2212
  rating: 1,
2129
2213
  num: 39,
@@ -2149,7 +2233,7 @@ exports.Abilities = {
2149
2233
  return null;
2150
2234
  }
2151
2235
  },
2152
- isBreakable: true,
2236
+ flags: { breakable: 1 },
2153
2237
  name: "Insomnia",
2154
2238
  rating: 1.5,
2155
2239
  num: 15,
@@ -2170,6 +2254,7 @@ exports.Abilities = {
2170
2254
  }
2171
2255
  }
2172
2256
  },
2257
+ flags: {},
2173
2258
  name: "Intimidate",
2174
2259
  rating: 3.5,
2175
2260
  num: 22,
@@ -2181,6 +2266,7 @@ exports.Abilities = {
2181
2266
  pokemon.swordBoost = true;
2182
2267
  this.boost({ atk: 1 }, pokemon);
2183
2268
  },
2269
+ flags: {},
2184
2270
  name: "Intrepid Sword",
2185
2271
  rating: 4,
2186
2272
  num: 234,
@@ -2192,6 +2278,7 @@ exports.Abilities = {
2192
2278
  this.damage(source.baseMaxhp / 8, source, target);
2193
2279
  }
2194
2280
  },
2281
+ flags: {},
2195
2282
  name: "Iron Barbs",
2196
2283
  rating: 2.5,
2197
2284
  num: 160,
@@ -2204,6 +2291,7 @@ exports.Abilities = {
2204
2291
  return this.chainModify([4915, 4096]);
2205
2292
  }
2206
2293
  },
2294
+ flags: {},
2207
2295
  name: "Iron Fist",
2208
2296
  rating: 3,
2209
2297
  num: 89,
@@ -2214,6 +2302,7 @@ exports.Abilities = {
2214
2302
  this.boost({ atk: 1 });
2215
2303
  }
2216
2304
  },
2305
+ flags: {},
2217
2306
  name: "Justified",
2218
2307
  rating: 2.5,
2219
2308
  num: 154,
@@ -2232,7 +2321,7 @@ exports.Abilities = {
2232
2321
  onModifyMove(move) {
2233
2322
  move.ignoreEvasion = true;
2234
2323
  },
2235
- isBreakable: true,
2324
+ flags: { breakable: 1 },
2236
2325
  name: "Keen Eye",
2237
2326
  rating: 0.5,
2238
2327
  num: 51,
@@ -2242,6 +2331,7 @@ exports.Abilities = {
2242
2331
  onStart(pokemon) {
2243
2332
  this.singleEvent('End', pokemon.getItem(), pokemon.itemState, pokemon);
2244
2333
  },
2334
+ flags: {},
2245
2335
  name: "Klutz",
2246
2336
  rating: -1,
2247
2337
  num: 103,
@@ -2261,14 +2351,14 @@ exports.Abilities = {
2261
2351
  return null;
2262
2352
  }
2263
2353
  },
2264
- isBreakable: true,
2354
+ flags: { breakable: 1 },
2265
2355
  name: "Leaf Guard",
2266
2356
  rating: 0.5,
2267
2357
  num: 102,
2268
2358
  },
2269
2359
  levitate: {
2270
2360
  // airborneness implemented in sim/pokemon.js:Pokemon#isGrounded
2271
- isBreakable: true,
2361
+ flags: { breakable: 1 },
2272
2362
  name: "Levitate",
2273
2363
  rating: 3.5,
2274
2364
  num: 26,
@@ -2290,6 +2380,7 @@ exports.Abilities = {
2290
2380
  onSwitchIn() {
2291
2381
  delete this.effectState.libero;
2292
2382
  },
2383
+ flags: {},
2293
2384
  name: "Libero",
2294
2385
  rating: 4,
2295
2386
  num: 236,
@@ -2298,7 +2389,7 @@ exports.Abilities = {
2298
2389
  onModifyWeight(weighthg) {
2299
2390
  return this.trunc(weighthg / 2);
2300
2391
  },
2301
- isBreakable: true,
2392
+ flags: { breakable: 1 },
2302
2393
  name: "Light Metal",
2303
2394
  rating: 1,
2304
2395
  num: 135,
@@ -2325,7 +2416,7 @@ exports.Abilities = {
2325
2416
  return this.effectState.target;
2326
2417
  }
2327
2418
  },
2328
- isBreakable: true,
2419
+ flags: { breakable: 1 },
2329
2420
  name: "Lightning Rod",
2330
2421
  rating: 3,
2331
2422
  num: 31,
@@ -2345,7 +2436,7 @@ exports.Abilities = {
2345
2436
  }
2346
2437
  return false;
2347
2438
  },
2348
- isBreakable: true,
2439
+ flags: { breakable: 1 },
2349
2440
  name: "Limber",
2350
2441
  rating: 2,
2351
2442
  num: 7,
@@ -2353,7 +2444,7 @@ exports.Abilities = {
2353
2444
  lingeringaroma: {
2354
2445
  onDamagingHit(damage, target, source, move) {
2355
2446
  const sourceAbility = source.getAbility();
2356
- if (sourceAbility.isPermanent || sourceAbility.id === 'lingeringaroma') {
2447
+ if (sourceAbility.flags['cantsuppress'] || sourceAbility.id === 'lingeringaroma') {
2357
2448
  return;
2358
2449
  }
2359
2450
  if (this.checkMoveMakesContact(move, source, target, !source.isAlly(target))) {
@@ -2363,6 +2454,7 @@ exports.Abilities = {
2363
2454
  }
2364
2455
  }
2365
2456
  },
2457
+ flags: {},
2366
2458
  name: "Lingering Aroma",
2367
2459
  rating: 2,
2368
2460
  num: 268,
@@ -2376,6 +2468,7 @@ exports.Abilities = {
2376
2468
  return 0;
2377
2469
  }
2378
2470
  },
2471
+ flags: {},
2379
2472
  name: "Liquid Ooze",
2380
2473
  rating: 2.5,
2381
2474
  num: 64,
@@ -2387,6 +2480,7 @@ exports.Abilities = {
2387
2480
  move.type = 'Water';
2388
2481
  }
2389
2482
  },
2483
+ flags: {},
2390
2484
  name: "Liquid Voice",
2391
2485
  rating: 1.5,
2392
2486
  num: 204,
@@ -2395,12 +2489,12 @@ exports.Abilities = {
2395
2489
  onModifyMove(move) {
2396
2490
  delete move.flags['contact'];
2397
2491
  },
2492
+ flags: {},
2398
2493
  name: "Long Reach",
2399
2494
  rating: 1,
2400
2495
  num: 203,
2401
2496
  },
2402
2497
  magicbounce: {
2403
- name: "Magic Bounce",
2404
2498
  onTryHitPriority: 1,
2405
2499
  onTryHit(target, source, move) {
2406
2500
  if (target === source || move.hasBounced || !move.flags['reflectable']) {
@@ -2425,7 +2519,8 @@ exports.Abilities = {
2425
2519
  condition: {
2426
2520
  duration: 1,
2427
2521
  },
2428
- isBreakable: true,
2522
+ flags: { breakable: 1 },
2523
+ name: "Magic Bounce",
2429
2524
  rating: 4,
2430
2525
  num: 156,
2431
2526
  },
@@ -2437,6 +2532,7 @@ exports.Abilities = {
2437
2532
  return false;
2438
2533
  }
2439
2534
  },
2535
+ flags: {},
2440
2536
  name: "Magic Guard",
2441
2537
  rating: 4,
2442
2538
  num: 98,
@@ -2458,6 +2554,7 @@ exports.Abilities = {
2458
2554
  this.add('-item', source, yourItem, '[from] ability: Magician', '[of] ' + target);
2459
2555
  }
2460
2556
  },
2557
+ flags: {},
2461
2558
  name: "Magician",
2462
2559
  rating: 1,
2463
2560
  num: 170,
@@ -2473,7 +2570,7 @@ exports.Abilities = {
2473
2570
  if (type === 'frz')
2474
2571
  return false;
2475
2572
  },
2476
- isBreakable: true,
2573
+ flags: { breakable: 1 },
2477
2574
  name: "Magma Armor",
2478
2575
  rating: 0.5,
2479
2576
  num: 40,
@@ -2493,6 +2590,7 @@ exports.Abilities = {
2493
2590
  pokemon.maybeTrapped = true;
2494
2591
  }
2495
2592
  },
2593
+ flags: {},
2496
2594
  name: "Magnet Pull",
2497
2595
  rating: 4,
2498
2596
  num: 42,
@@ -2504,7 +2602,7 @@ exports.Abilities = {
2504
2602
  return this.chainModify(1.5);
2505
2603
  }
2506
2604
  },
2507
- isBreakable: true,
2605
+ flags: { breakable: 1 },
2508
2606
  name: "Marvel Scale",
2509
2607
  rating: 2.5,
2510
2608
  num: 63,
@@ -2516,6 +2614,7 @@ exports.Abilities = {
2516
2614
  return this.chainModify(1.5);
2517
2615
  }
2518
2616
  },
2617
+ flags: {},
2519
2618
  name: "Mega Launcher",
2520
2619
  rating: 3,
2521
2620
  num: 178,
@@ -2525,6 +2624,7 @@ exports.Abilities = {
2525
2624
  if (target && ['psn', 'tox'].includes(target.status))
2526
2625
  return 5;
2527
2626
  },
2627
+ flags: {},
2528
2628
  name: "Merciless",
2529
2629
  rating: 1.5,
2530
2630
  num: 196,
@@ -2564,6 +2664,7 @@ exports.Abilities = {
2564
2664
  this.add('-end', pokemon, 'typechange', '[silent]');
2565
2665
  }
2566
2666
  },
2667
+ flags: {},
2567
2668
  name: "Mimicry",
2568
2669
  rating: 0,
2569
2670
  num: 250,
@@ -2589,6 +2690,7 @@ exports.Abilities = {
2589
2690
  move.ignoreImmunity['Normal'] = true;
2590
2691
  }
2591
2692
  },
2693
+ flags: { breakable: 1 },
2592
2694
  name: "Mind's Eye",
2593
2695
  rating: 0,
2594
2696
  num: 300,
@@ -2602,6 +2704,7 @@ exports.Abilities = {
2602
2704
  }
2603
2705
  }
2604
2706
  },
2707
+ flags: {},
2605
2708
  name: "Minus",
2606
2709
  rating: 0,
2607
2710
  num: 58,
@@ -2626,7 +2729,7 @@ exports.Abilities = {
2626
2729
  }
2627
2730
  }
2628
2731
  },
2629
- isBreakable: true,
2732
+ flags: { breakable: 1 },
2630
2733
  name: "Mirror Armor",
2631
2734
  rating: 2,
2632
2735
  num: 240,
@@ -2635,6 +2738,7 @@ exports.Abilities = {
2635
2738
  onStart(source) {
2636
2739
  this.field.setTerrain('mistyterrain');
2637
2740
  },
2741
+ flags: {},
2638
2742
  name: "Misty Surge",
2639
2743
  rating: 3.5,
2640
2744
  num: 228,
@@ -2646,6 +2750,7 @@ exports.Abilities = {
2646
2750
  onModifyMove(move) {
2647
2751
  move.ignoreAbility = true;
2648
2752
  },
2753
+ flags: {},
2649
2754
  name: "Mold Breaker",
2650
2755
  rating: 3,
2651
2756
  num: 104,
@@ -2681,6 +2786,7 @@ exports.Abilities = {
2681
2786
  boost[randomStat] = -1;
2682
2787
  this.boost(boost, pokemon, pokemon);
2683
2788
  },
2789
+ flags: {},
2684
2790
  name: "Moody",
2685
2791
  rating: 5,
2686
2792
  num: 141,
@@ -2694,7 +2800,7 @@ exports.Abilities = {
2694
2800
  return null;
2695
2801
  }
2696
2802
  },
2697
- isBreakable: true,
2803
+ flags: { breakable: 1 },
2698
2804
  name: "Motor Drive",
2699
2805
  rating: 3,
2700
2806
  num: 78,
@@ -2705,6 +2811,7 @@ exports.Abilities = {
2705
2811
  this.boost({ atk: length }, source);
2706
2812
  }
2707
2813
  },
2814
+ flags: {},
2708
2815
  name: "Moxie",
2709
2816
  rating: 3,
2710
2817
  num: 153,
@@ -2716,23 +2823,22 @@ exports.Abilities = {
2716
2823
  return this.chainModify(0.5);
2717
2824
  }
2718
2825
  },
2719
- isBreakable: true,
2826
+ flags: { breakable: 1 },
2720
2827
  name: "Multiscale",
2721
2828
  rating: 3.5,
2722
2829
  num: 136,
2723
2830
  },
2724
2831
  multitype: {
2725
2832
  // Multitype's type-changing itself is implemented in statuses.js
2726
- isPermanent: true,
2833
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
2727
2834
  name: "Multitype",
2728
2835
  rating: 4,
2729
2836
  num: 121,
2730
2837
  },
2731
2838
  mummy: {
2732
- name: "Mummy",
2733
2839
  onDamagingHit(damage, target, source, move) {
2734
2840
  const sourceAbility = source.getAbility();
2735
- if (sourceAbility.isPermanent || sourceAbility.id === 'mummy') {
2841
+ if (sourceAbility.flags['cantsuppress'] || sourceAbility.id === 'mummy') {
2736
2842
  return;
2737
2843
  }
2738
2844
  if (this.checkMoveMakesContact(move, source, target, !source.isAlly(target))) {
@@ -2742,6 +2848,8 @@ exports.Abilities = {
2742
2848
  }
2743
2849
  }
2744
2850
  },
2851
+ flags: {},
2852
+ name: "Mummy",
2745
2853
  rating: 2,
2746
2854
  num: 152,
2747
2855
  },
@@ -2757,6 +2865,7 @@ exports.Abilities = {
2757
2865
  move.ignoreAbility = true;
2758
2866
  }
2759
2867
  },
2868
+ flags: {},
2760
2869
  name: "Mycelium Might",
2761
2870
  rating: 2,
2762
2871
  num: 298,
@@ -2839,6 +2948,7 @@ exports.Abilities = {
2839
2948
  if (!pokemon.showCure)
2840
2949
  pokemon.showCure = undefined;
2841
2950
  },
2951
+ flags: {},
2842
2952
  name: "Natural Cure",
2843
2953
  rating: 2.5,
2844
2954
  num: 30,
@@ -2849,6 +2959,7 @@ exports.Abilities = {
2849
2959
  return this.chainModify([5120, 4096]);
2850
2960
  }
2851
2961
  },
2962
+ flags: {},
2852
2963
  name: "Neuroforce",
2853
2964
  rating: 2.5,
2854
2965
  num: 233,
@@ -2856,8 +2967,6 @@ exports.Abilities = {
2856
2967
  neutralizinggas: {
2857
2968
  // Ability suppression implemented in sim/pokemon.ts:Pokemon#ignoringAbility
2858
2969
  onPreStart(pokemon) {
2859
- if (pokemon.transformed)
2860
- return;
2861
2970
  this.add('-ability', pokemon, 'Neutralizing Gas');
2862
2971
  pokemon.abilityState.ending = false;
2863
2972
  const strongWeathers = ['desolateland', 'primordialsea', 'deltastream'];
@@ -2903,7 +3012,7 @@ exports.Abilities = {
2903
3012
  this.speedSort(sortedActive);
2904
3013
  for (const pokemon of sortedActive) {
2905
3014
  if (pokemon !== source) {
2906
- if (pokemon.getAbility().isPermanent)
3015
+ if (pokemon.getAbility().flags['cantsuppress'])
2907
3016
  continue; // does not interact with e.g Ice Face, Zen Mode
2908
3017
  if (pokemon.hasItem('abilityshield'))
2909
3018
  continue; // don't restart abilities that weren't suppressed
@@ -2915,6 +3024,7 @@ exports.Abilities = {
2915
3024
  }
2916
3025
  }
2917
3026
  },
3027
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
2918
3028
  name: "Neutralizing Gas",
2919
3029
  rating: 3.5,
2920
3030
  num: 256,
@@ -2931,6 +3041,7 @@ exports.Abilities = {
2931
3041
  }
2932
3042
  return accuracy;
2933
3043
  },
3044
+ flags: {},
2934
3045
  name: "No Guard",
2935
3046
  rating: 4,
2936
3047
  num: 99,
@@ -2953,6 +3064,7 @@ exports.Abilities = {
2953
3064
  if (move.typeChangerBoosted === this.effect)
2954
3065
  return this.chainModify([4915, 4096]);
2955
3066
  },
3067
+ flags: {},
2956
3068
  name: "Normalize",
2957
3069
  rating: 0,
2958
3070
  num: 96,
@@ -2986,7 +3098,7 @@ exports.Abilities = {
2986
3098
  this.add('-fail', target, 'unboost', 'Attack', '[from] ability: Oblivious', '[of] ' + target);
2987
3099
  }
2988
3100
  },
2989
- isBreakable: true,
3101
+ flags: { breakable: 1 },
2990
3102
  name: "Oblivious",
2991
3103
  rating: 1.5,
2992
3104
  num: 12,
@@ -3007,6 +3119,7 @@ exports.Abilities = {
3007
3119
  return;
3008
3120
  this.boost(positiveBoosts, pokemon);
3009
3121
  },
3122
+ flags: {},
3010
3123
  name: "Opportunist",
3011
3124
  rating: 3,
3012
3125
  num: 290,
@@ -3027,6 +3140,7 @@ exports.Abilities = {
3027
3140
  return this.chainModify([5461, 4096]);
3028
3141
  }
3029
3142
  },
3143
+ flags: {},
3030
3144
  name: "Orichalcum Pulse",
3031
3145
  rating: 4.5,
3032
3146
  num: 288,
@@ -3043,7 +3157,7 @@ exports.Abilities = {
3043
3157
  return null;
3044
3158
  }
3045
3159
  },
3046
- isBreakable: true,
3160
+ flags: { breakable: 1 },
3047
3161
  name: "Overcoat",
3048
3162
  rating: 2,
3049
3163
  num: 142,
@@ -3063,6 +3177,7 @@ exports.Abilities = {
3063
3177
  return this.chainModify(1.5);
3064
3178
  }
3065
3179
  },
3180
+ flags: {},
3066
3181
  name: "Overgrow",
3067
3182
  rating: 2,
3068
3183
  num: 65,
@@ -3089,7 +3204,7 @@ exports.Abilities = {
3089
3204
  this.add('-fail', target, 'unboost', 'Attack', '[from] ability: Own Tempo', '[of] ' + target);
3090
3205
  }
3091
3206
  },
3092
- isBreakable: true,
3207
+ flags: { breakable: 1 },
3093
3208
  name: "Own Tempo",
3094
3209
  rating: 1.5,
3095
3210
  num: 20,
@@ -3109,6 +3224,7 @@ exports.Abilities = {
3109
3224
  return secondaries.filter(effect => effect.volatileStatus === 'flinch');
3110
3225
  }
3111
3226
  },
3227
+ flags: {},
3112
3228
  name: "Parental Bond",
3113
3229
  rating: 4.5,
3114
3230
  num: 185,
@@ -3151,7 +3267,7 @@ exports.Abilities = {
3151
3267
  }
3152
3268
  return false;
3153
3269
  },
3154
- isBreakable: true,
3270
+ flags: { breakable: 1 },
3155
3271
  name: "Pastel Veil",
3156
3272
  rating: 2,
3157
3273
  num: 257,
@@ -3171,6 +3287,7 @@ exports.Abilities = {
3171
3287
  pokemon.addVolatile('perishsong');
3172
3288
  }
3173
3289
  },
3290
+ flags: {},
3174
3291
  name: "Perish Body",
3175
3292
  rating: 1,
3176
3293
  num: 253,
@@ -3193,6 +3310,7 @@ exports.Abilities = {
3193
3310
  this.add('-item', target, yourItem, '[from] ability: Pickpocket', '[of] ' + source);
3194
3311
  }
3195
3312
  },
3313
+ flags: {},
3196
3314
  name: "Pickpocket",
3197
3315
  rating: 1,
3198
3316
  num: 124,
@@ -3212,6 +3330,7 @@ exports.Abilities = {
3212
3330
  this.add('-item', pokemon, this.dex.items.get(item), '[from] ability: Pickup');
3213
3331
  pokemon.setItem(item);
3214
3332
  },
3333
+ flags: {},
3215
3334
  name: "Pickup",
3216
3335
  rating: 0.5,
3217
3336
  num: 53,
@@ -3233,6 +3352,7 @@ exports.Abilities = {
3233
3352
  if (move.typeChangerBoosted === this.effect)
3234
3353
  return this.chainModify([4915, 4096]);
3235
3354
  },
3355
+ flags: {},
3236
3356
  name: "Pixilate",
3237
3357
  rating: 4,
3238
3358
  num: 182,
@@ -3246,6 +3366,7 @@ exports.Abilities = {
3246
3366
  }
3247
3367
  }
3248
3368
  },
3369
+ flags: {},
3249
3370
  name: "Plus",
3250
3371
  rating: 0,
3251
3372
  num: 57,
@@ -3258,6 +3379,7 @@ exports.Abilities = {
3258
3379
  return false;
3259
3380
  }
3260
3381
  },
3382
+ flags: {},
3261
3383
  name: "Poison Heal",
3262
3384
  rating: 4,
3263
3385
  num: 90,
@@ -3270,18 +3392,22 @@ exports.Abilities = {
3270
3392
  }
3271
3393
  }
3272
3394
  },
3395
+ flags: {},
3273
3396
  name: "Poison Point",
3274
3397
  rating: 1.5,
3275
3398
  num: 38,
3276
3399
  },
3277
3400
  poisonpuppeteer: {
3278
3401
  onAnyAfterSetStatus(status, target, source, effect) {
3402
+ if (source.baseSpecies.name !== "Pecharunt")
3403
+ return;
3279
3404
  if (source !== this.effectState.target || target === source || effect.effectType !== 'Move')
3280
3405
  return;
3281
3406
  if (status.id === 'psn' || status.id === 'tox') {
3282
3407
  target.addVolatile('confusion');
3283
3408
  }
3284
3409
  },
3410
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1 },
3285
3411
  name: "Poison Puppeteer",
3286
3412
  rating: 3,
3287
3413
  num: 310,
@@ -3297,6 +3423,7 @@ exports.Abilities = {
3297
3423
  }
3298
3424
  }
3299
3425
  },
3426
+ flags: {},
3300
3427
  name: "Poison Touch",
3301
3428
  rating: 2,
3302
3429
  num: 143,
@@ -3316,7 +3443,7 @@ exports.Abilities = {
3316
3443
  pokemon.maxhp = newMaxHP;
3317
3444
  this.add('-heal', pokemon, pokemon.getHealth, '[silent]');
3318
3445
  },
3319
- isPermanent: true,
3446
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
3320
3447
  name: "Power Construct",
3321
3448
  rating: 5,
3322
3449
  num: 211,
@@ -3326,15 +3453,13 @@ exports.Abilities = {
3326
3453
  if (!this.effectState.target.hp)
3327
3454
  return;
3328
3455
  const ability = target.getAbility();
3329
- const additionalBannedAbilities = [
3330
- 'noability', 'commander', 'flowergift', 'forecast', 'hungerswitch', 'illusion', 'imposter', 'neutralizinggas', 'powerofalchemy', 'receiver', 'trace', 'wonderguard',
3331
- ];
3332
- if (target.getAbility().isPermanent || additionalBannedAbilities.includes(target.ability))
3456
+ if (ability.flags['noreceiver'] || ability.id === 'noability')
3333
3457
  return;
3334
3458
  if (this.effectState.target.setAbility(ability)) {
3335
3459
  this.add('-ability', this.effectState.target, ability, '[from] ability: Power of Alchemy', '[of] ' + target);
3336
3460
  }
3337
3461
  },
3462
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1 },
3338
3463
  name: "Power of Alchemy",
3339
3464
  rating: 0,
3340
3465
  num: 223,
@@ -3347,6 +3472,7 @@ exports.Abilities = {
3347
3472
  return this.chainModify([5325, 4096]);
3348
3473
  }
3349
3474
  },
3475
+ flags: {},
3350
3476
  name: "Power Spot",
3351
3477
  rating: 0,
3352
3478
  num: 249,
@@ -3358,6 +3484,7 @@ exports.Abilities = {
3358
3484
  return priority + 1;
3359
3485
  }
3360
3486
  },
3487
+ flags: {},
3361
3488
  name: "Prankster",
3362
3489
  rating: 4,
3363
3490
  num: 158,
@@ -3371,6 +3498,7 @@ exports.Abilities = {
3371
3498
  return;
3372
3499
  return 1;
3373
3500
  },
3501
+ flags: {},
3374
3502
  name: "Pressure",
3375
3503
  rating: 2.5,
3376
3504
  num: 46,
@@ -3397,6 +3525,7 @@ exports.Abilities = {
3397
3525
  }
3398
3526
  this.field.clearWeather();
3399
3527
  },
3528
+ flags: {},
3400
3529
  name: "Primordial Sea",
3401
3530
  rating: 4.5,
3402
3531
  num: 189,
@@ -3408,6 +3537,7 @@ exports.Abilities = {
3408
3537
  return this.chainModify(0.75);
3409
3538
  }
3410
3539
  },
3540
+ flags: {},
3411
3541
  name: "Prism Armor",
3412
3542
  rating: 3,
3413
3543
  num: 232,
@@ -3418,6 +3548,7 @@ exports.Abilities = {
3418
3548
  // most of the implementation is in Battle#getTarget
3419
3549
  move.tracksTarget = move.target !== 'scripted';
3420
3550
  },
3551
+ flags: {},
3421
3552
  name: "Propeller Tail",
3422
3553
  rating: 0,
3423
3554
  num: 239,
@@ -3439,6 +3570,7 @@ exports.Abilities = {
3439
3570
  onSwitchIn(pokemon) {
3440
3571
  delete this.effectState.protean;
3441
3572
  },
3573
+ flags: {},
3442
3574
  name: "Protean",
3443
3575
  rating: 4,
3444
3576
  num: 168,
@@ -3448,8 +3580,6 @@ exports.Abilities = {
3448
3580
  this.singleEvent('WeatherChange', this.effect, this.effectState, pokemon);
3449
3581
  },
3450
3582
  onWeatherChange(pokemon) {
3451
- if (pokemon.transformed)
3452
- return;
3453
3583
  // Protosynthesis is not affected by Utility Umbrella
3454
3584
  if (this.field.isWeather('sunnyday')) {
3455
3585
  pokemon.addVolatile('protosynthesis');
@@ -3513,6 +3643,7 @@ exports.Abilities = {
3513
3643
  this.add('-end', pokemon, 'Protosynthesis');
3514
3644
  },
3515
3645
  },
3646
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
3516
3647
  name: "Protosynthesis",
3517
3648
  rating: 3,
3518
3649
  num: 281,
@@ -3521,6 +3652,7 @@ exports.Abilities = {
3521
3652
  onStart(source) {
3522
3653
  this.field.setTerrain('psychicterrain');
3523
3654
  },
3655
+ flags: {},
3524
3656
  name: "Psychic Surge",
3525
3657
  rating: 4,
3526
3658
  num: 227,
@@ -3539,7 +3671,7 @@ exports.Abilities = {
3539
3671
  return this.chainModify(0.5);
3540
3672
  }
3541
3673
  },
3542
- isBreakable: true,
3674
+ flags: { breakable: 1 },
3543
3675
  name: "Punk Rock",
3544
3676
  rating: 3.5,
3545
3677
  num: 244,
@@ -3549,6 +3681,7 @@ exports.Abilities = {
3549
3681
  onModifyAtk(atk) {
3550
3682
  return this.chainModify(2);
3551
3683
  },
3684
+ flags: {},
3552
3685
  name: "Pure Power",
3553
3686
  rating: 5,
3554
3687
  num: 74,
@@ -3580,7 +3713,7 @@ exports.Abilities = {
3580
3713
  return this.chainModify(0.5);
3581
3714
  }
3582
3715
  },
3583
- isBreakable: true,
3716
+ flags: { breakable: 1 },
3584
3717
  name: "Purifying Salt",
3585
3718
  rating: 4,
3586
3719
  num: 272,
@@ -3590,8 +3723,6 @@ exports.Abilities = {
3590
3723
  this.singleEvent('TerrainChange', this.effect, this.effectState, pokemon);
3591
3724
  },
3592
3725
  onTerrainChange(pokemon) {
3593
- if (pokemon.transformed)
3594
- return;
3595
3726
  if (this.field.isTerrain('electricterrain')) {
3596
3727
  pokemon.addVolatile('quarkdrive');
3597
3728
  }
@@ -3654,6 +3785,7 @@ exports.Abilities = {
3654
3785
  this.add('-end', pokemon, 'Quark Drive');
3655
3786
  },
3656
3787
  },
3788
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, notransform: 1 },
3657
3789
  name: "Quark Drive",
3658
3790
  rating: 3,
3659
3791
  num: 282,
@@ -3671,7 +3803,7 @@ exports.Abilities = {
3671
3803
  return false;
3672
3804
  }
3673
3805
  },
3674
- isBreakable: true,
3806
+ flags: { breakable: 1 },
3675
3807
  name: "Queenly Majesty",
3676
3808
  rating: 2.5,
3677
3809
  num: 214,
@@ -3684,6 +3816,7 @@ exports.Abilities = {
3684
3816
  return 0.1;
3685
3817
  }
3686
3818
  },
3819
+ flags: {},
3687
3820
  name: "Quick Draw",
3688
3821
  rating: 2.5,
3689
3822
  num: 259,
@@ -3694,6 +3827,7 @@ exports.Abilities = {
3694
3827
  return this.chainModify(1.5);
3695
3828
  }
3696
3829
  },
3830
+ flags: {},
3697
3831
  name: "Quick Feet",
3698
3832
  rating: 2.5,
3699
3833
  num: 95,
@@ -3706,6 +3840,7 @@ exports.Abilities = {
3706
3840
  this.heal(target.baseMaxhp / 16);
3707
3841
  }
3708
3842
  },
3843
+ flags: {},
3709
3844
  name: "Rain Dish",
3710
3845
  rating: 1.5,
3711
3846
  num: 44,
@@ -3721,6 +3856,7 @@ exports.Abilities = {
3721
3856
  this.boost({ spe: 1 });
3722
3857
  }
3723
3858
  },
3859
+ flags: {},
3724
3860
  name: "Rattled",
3725
3861
  rating: 1,
3726
3862
  num: 155,
@@ -3730,15 +3866,13 @@ exports.Abilities = {
3730
3866
  if (!this.effectState.target.hp)
3731
3867
  return;
3732
3868
  const ability = target.getAbility();
3733
- const additionalBannedAbilities = [
3734
- 'noability', 'commander', 'flowergift', 'forecast', 'hungerswitch', 'illusion', 'imposter', 'neutralizinggas', 'powerofalchemy', 'receiver', 'trace', 'wonderguard',
3735
- ];
3736
- if (target.getAbility().isPermanent || additionalBannedAbilities.includes(target.ability))
3869
+ if (ability.flags['noreceiver'] || ability.id === 'noability')
3737
3870
  return;
3738
3871
  if (this.effectState.target.setAbility(ability)) {
3739
3872
  this.add('-ability', this.effectState.target, ability, '[from] ability: Receiver', '[of] ' + target);
3740
3873
  }
3741
3874
  },
3875
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1 },
3742
3876
  name: "Receiver",
3743
3877
  rating: 0,
3744
3878
  num: 222,
@@ -3751,6 +3885,7 @@ exports.Abilities = {
3751
3885
  return this.chainModify([4915, 4096]);
3752
3886
  }
3753
3887
  },
3888
+ flags: {},
3754
3889
  name: "Reckless",
3755
3890
  rating: 3,
3756
3891
  num: 120,
@@ -3772,6 +3907,7 @@ exports.Abilities = {
3772
3907
  if (move.typeChangerBoosted === this.effect)
3773
3908
  return this.chainModify([4915, 4096]);
3774
3909
  },
3910
+ flags: {},
3775
3911
  name: "Refrigerate",
3776
3912
  rating: 4,
3777
3913
  num: 174,
@@ -3780,6 +3916,7 @@ exports.Abilities = {
3780
3916
  onSwitchOut(pokemon) {
3781
3917
  pokemon.heal(pokemon.baseMaxhp / 3);
3782
3918
  },
3919
+ flags: {},
3783
3920
  name: "Regenerator",
3784
3921
  rating: 4.5,
3785
3922
  num: 144,
@@ -3820,6 +3957,7 @@ exports.Abilities = {
3820
3957
  // Record if the pokemon ate a berry to resist the attack
3821
3958
  pokemon.abilityState.berryWeaken = weakenBerries.includes(item.name);
3822
3959
  },
3960
+ flags: {},
3823
3961
  name: "Ripen",
3824
3962
  rating: 2,
3825
3963
  num: 247,
@@ -3838,13 +3976,14 @@ exports.Abilities = {
3838
3976
  }
3839
3977
  }
3840
3978
  },
3979
+ flags: {},
3841
3980
  name: "Rivalry",
3842
3981
  rating: 0,
3843
3982
  num: 79,
3844
3983
  },
3845
3984
  rkssystem: {
3846
3985
  // RKS System's type-changing itself is implemented in statuses.js
3847
- isPermanent: true,
3986
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
3848
3987
  name: "RKS System",
3849
3988
  rating: 4,
3850
3989
  num: 225,
@@ -3858,6 +3997,7 @@ exports.Abilities = {
3858
3997
  return null;
3859
3998
  }
3860
3999
  },
4000
+ flags: {},
3861
4001
  name: "Rock Head",
3862
4002
  rating: 3,
3863
4003
  num: 69,
@@ -3877,6 +4017,7 @@ exports.Abilities = {
3877
4017
  return this.chainModify(1.5);
3878
4018
  }
3879
4019
  },
4020
+ flags: {},
3880
4021
  name: "Rocky Payload",
3881
4022
  rating: 3.5,
3882
4023
  num: 276,
@@ -3888,11 +4029,13 @@ exports.Abilities = {
3888
4029
  this.damage(source.baseMaxhp / 8, source, target);
3889
4030
  }
3890
4031
  },
4032
+ flags: {},
3891
4033
  name: "Rough Skin",
3892
4034
  rating: 2.5,
3893
4035
  num: 24,
3894
4036
  },
3895
4037
  runaway: {
4038
+ flags: {},
3896
4039
  name: "Run Away",
3897
4040
  rating: 0,
3898
4041
  num: 50,
@@ -3911,6 +4054,7 @@ exports.Abilities = {
3911
4054
  if (type === 'sandstorm')
3912
4055
  return false;
3913
4056
  },
4057
+ flags: {},
3914
4058
  name: "Sand Force",
3915
4059
  rating: 2,
3916
4060
  num: 159,
@@ -3925,6 +4069,7 @@ exports.Abilities = {
3925
4069
  if (type === 'sandstorm')
3926
4070
  return false;
3927
4071
  },
4072
+ flags: {},
3928
4073
  name: "Sand Rush",
3929
4074
  rating: 3,
3930
4075
  num: 146,
@@ -3933,6 +4078,7 @@ exports.Abilities = {
3933
4078
  onDamagingHit(damage, target, source, move) {
3934
4079
  this.field.setWeather('sandstorm');
3935
4080
  },
4081
+ flags: {},
3936
4082
  name: "Sand Spit",
3937
4083
  rating: 1,
3938
4084
  num: 245,
@@ -3941,6 +4087,7 @@ exports.Abilities = {
3941
4087
  onStart(source) {
3942
4088
  this.field.setWeather('sandstorm');
3943
4089
  },
4090
+ flags: {},
3944
4091
  name: "Sand Stream",
3945
4092
  rating: 4,
3946
4093
  num: 45,
@@ -3959,7 +4106,7 @@ exports.Abilities = {
3959
4106
  return this.chainModify([3277, 4096]);
3960
4107
  }
3961
4108
  },
3962
- isBreakable: true,
4109
+ flags: { breakable: 1 },
3963
4110
  name: "Sand Veil",
3964
4111
  rating: 1.5,
3965
4112
  num: 8,
@@ -3981,7 +4128,7 @@ exports.Abilities = {
3981
4128
  this.boost({ atk: 1 }, this.effectState.target);
3982
4129
  }
3983
4130
  },
3984
- isBreakable: true,
4131
+ flags: { breakable: 1 },
3985
4132
  name: "Sap Sipper",
3986
4133
  rating: 3,
3987
4134
  num: 157,
@@ -4017,7 +4164,7 @@ exports.Abilities = {
4017
4164
  }
4018
4165
  }
4019
4166
  },
4020
- isPermanent: true,
4167
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
4021
4168
  name: "Schooling",
4022
4169
  rating: 3,
4023
4170
  num: 208,
@@ -4038,6 +4185,7 @@ exports.Abilities = {
4038
4185
  this.add('-fail', target, 'unboost', 'Attack', '[from] ability: Scrappy', '[of] ' + target);
4039
4186
  }
4040
4187
  },
4188
+ flags: {},
4041
4189
  name: "Scrappy",
4042
4190
  rating: 3,
4043
4191
  num: 113,
@@ -4057,6 +4205,7 @@ exports.Abilities = {
4057
4205
  }
4058
4206
  }
4059
4207
  },
4208
+ flags: {},
4060
4209
  name: "Screen Cleaner",
4061
4210
  rating: 2,
4062
4211
  num: 251,
@@ -4065,6 +4214,7 @@ exports.Abilities = {
4065
4214
  onDamagingHit(damage, target, source, move) {
4066
4215
  this.field.setTerrain('grassyterrain');
4067
4216
  },
4217
+ flags: {},
4068
4218
  name: "Seed Sower",
4069
4219
  rating: 2.5,
4070
4220
  num: 269,
@@ -4082,6 +4232,7 @@ exports.Abilities = {
4082
4232
  if (move.self?.chance)
4083
4233
  move.self.chance *= 2;
4084
4234
  },
4235
+ flags: {},
4085
4236
  name: "Serene Grace",
4086
4237
  rating: 3.5,
4087
4238
  num: 32,
@@ -4093,6 +4244,7 @@ exports.Abilities = {
4093
4244
  return this.chainModify(0.5);
4094
4245
  }
4095
4246
  },
4247
+ flags: {},
4096
4248
  name: "Shadow Shield",
4097
4249
  rating: 3.5,
4098
4250
  num: 231,
@@ -4112,6 +4264,7 @@ exports.Abilities = {
4112
4264
  pokemon.maybeTrapped = true;
4113
4265
  }
4114
4266
  },
4267
+ flags: {},
4115
4268
  name: "Shadow Tag",
4116
4269
  rating: 5,
4117
4270
  num: 23,
@@ -4124,6 +4277,7 @@ exports.Abilities = {
4124
4277
  return this.chainModify(1.5);
4125
4278
  }
4126
4279
  },
4280
+ flags: {},
4127
4281
  name: "Sharpness",
4128
4282
  rating: 3.5,
4129
4283
  num: 292,
@@ -4138,6 +4292,7 @@ exports.Abilities = {
4138
4292
  pokemon.cureStatus();
4139
4293
  }
4140
4294
  },
4295
+ flags: {},
4141
4296
  name: "Shed Skin",
4142
4297
  rating: 3,
4143
4298
  num: 61,
@@ -4159,13 +4314,14 @@ exports.Abilities = {
4159
4314
  if (move.hasSheerForce)
4160
4315
  return this.chainModify([5325, 4096]);
4161
4316
  },
4317
+ flags: {},
4162
4318
  name: "Sheer Force",
4163
4319
  rating: 3.5,
4164
4320
  num: 125,
4165
4321
  },
4166
4322
  shellarmor: {
4167
4323
  onCriticalHit: false,
4168
- isBreakable: true,
4324
+ flags: { breakable: 1 },
4169
4325
  name: "Shell Armor",
4170
4326
  rating: 1,
4171
4327
  num: 75,
@@ -4175,7 +4331,7 @@ exports.Abilities = {
4175
4331
  this.debug('Shield Dust prevent secondary');
4176
4332
  return secondaries.filter(effect => !!(effect.self || effect.dustproof));
4177
4333
  },
4178
- isBreakable: true,
4334
+ flags: { breakable: 1 },
4179
4335
  name: "Shield Dust",
4180
4336
  rating: 2,
4181
4337
  num: 19,
@@ -4226,7 +4382,7 @@ exports.Abilities = {
4226
4382
  this.add('-immune', target, '[from] ability: Shields Down');
4227
4383
  return null;
4228
4384
  },
4229
- isPermanent: true,
4385
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
4230
4386
  name: "Shields Down",
4231
4387
  rating: 3,
4232
4388
  num: 197,
@@ -4240,7 +4396,7 @@ exports.Abilities = {
4240
4396
  boost[i] *= 2;
4241
4397
  }
4242
4398
  },
4243
- isBreakable: true,
4399
+ flags: { breakable: 1 },
4244
4400
  name: "Simple",
4245
4401
  rating: 4,
4246
4402
  num: 86,
@@ -4254,6 +4410,7 @@ exports.Abilities = {
4254
4410
  delete move.multiaccuracy;
4255
4411
  }
4256
4412
  },
4413
+ flags: {},
4257
4414
  name: "Skill Link",
4258
4415
  rating: 3,
4259
4416
  num: 92,
@@ -4284,6 +4441,7 @@ exports.Abilities = {
4284
4441
  this.add('-end', target, 'Slow Start');
4285
4442
  },
4286
4443
  },
4444
+ flags: {},
4287
4445
  name: "Slow Start",
4288
4446
  rating: -1,
4289
4447
  num: 112,
@@ -4294,6 +4452,7 @@ exports.Abilities = {
4294
4452
  return this.chainModify(2);
4295
4453
  }
4296
4454
  },
4455
+ flags: {},
4297
4456
  name: "Slush Rush",
4298
4457
  rating: 3,
4299
4458
  num: 202,
@@ -4305,6 +4464,7 @@ exports.Abilities = {
4305
4464
  return this.chainModify(1.5);
4306
4465
  }
4307
4466
  },
4467
+ flags: {},
4308
4468
  name: "Sniper",
4309
4469
  rating: 2,
4310
4470
  num: 97,
@@ -4323,7 +4483,7 @@ exports.Abilities = {
4323
4483
  return this.chainModify([3277, 4096]);
4324
4484
  }
4325
4485
  },
4326
- isBreakable: true,
4486
+ flags: { breakable: 1 },
4327
4487
  name: "Snow Cloak",
4328
4488
  rating: 1.5,
4329
4489
  num: 81,
@@ -4332,6 +4492,7 @@ exports.Abilities = {
4332
4492
  onStart(source) {
4333
4493
  this.field.setWeather('snow');
4334
4494
  },
4495
+ flags: {},
4335
4496
  name: "Snow Warning",
4336
4497
  rating: 4,
4337
4498
  num: 117,
@@ -4350,6 +4511,7 @@ exports.Abilities = {
4350
4511
  this.damage(target.baseMaxhp / 8, target, target);
4351
4512
  }
4352
4513
  },
4514
+ flags: {},
4353
4515
  name: "Solar Power",
4354
4516
  rating: 2,
4355
4517
  num: 94,
@@ -4361,7 +4523,7 @@ exports.Abilities = {
4361
4523
  return this.chainModify(0.75);
4362
4524
  }
4363
4525
  },
4364
- isBreakable: true,
4526
+ flags: { breakable: 1 },
4365
4527
  name: "Solid Rock",
4366
4528
  rating: 3,
4367
4529
  num: 116,
@@ -4371,6 +4533,7 @@ exports.Abilities = {
4371
4533
  onAnyFaint() {
4372
4534
  this.boost({ spa: 1 }, this.effectState.target);
4373
4535
  },
4536
+ flags: {},
4374
4537
  name: "Soul-Heart",
4375
4538
  rating: 3.5,
4376
4539
  num: 220,
@@ -4387,7 +4550,7 @@ exports.Abilities = {
4387
4550
  this.add('-immune', this.effectState.target, '[from] ability: Soundproof');
4388
4551
  }
4389
4552
  },
4390
- isBreakable: true,
4553
+ flags: { breakable: 1 },
4391
4554
  name: "Soundproof",
4392
4555
  rating: 2,
4393
4556
  num: 43,
@@ -4400,6 +4563,7 @@ exports.Abilities = {
4400
4563
  this.boost({ spe: 1 });
4401
4564
  }
4402
4565
  },
4566
+ flags: {},
4403
4567
  name: "Speed Boost",
4404
4568
  rating: 4.5,
4405
4569
  num: 3,
@@ -4419,12 +4583,14 @@ exports.Abilities = {
4419
4583
  return this.chainModify(2);
4420
4584
  }
4421
4585
  },
4586
+ flags: {},
4422
4587
  name: "Stakeout",
4423
4588
  rating: 4.5,
4424
4589
  num: 198,
4425
4590
  },
4426
4591
  stall: {
4427
4592
  onFractionalPriority: -0.1,
4593
+ flags: {},
4428
4594
  name: "Stall",
4429
4595
  rating: -1,
4430
4596
  num: 100,
@@ -4435,6 +4601,7 @@ exports.Abilities = {
4435
4601
  // most of the implementation is in Battle#getTarget
4436
4602
  move.tracksTarget = move.target !== 'scripted';
4437
4603
  },
4604
+ flags: {},
4438
4605
  name: "Stalwart",
4439
4606
  rating: 0,
4440
4607
  num: 242,
@@ -4443,6 +4610,7 @@ exports.Abilities = {
4443
4610
  onDamagingHit(damage, target, source, effect) {
4444
4611
  this.boost({ def: 1 });
4445
4612
  },
4613
+ flags: {},
4446
4614
  name: "Stamina",
4447
4615
  rating: 4,
4448
4616
  num: 192,
@@ -4458,7 +4626,7 @@ exports.Abilities = {
4458
4626
  if (attacker.species.name !== targetForme)
4459
4627
  attacker.formeChange(targetForme);
4460
4628
  },
4461
- isPermanent: true,
4629
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
4462
4630
  name: "Stance Change",
4463
4631
  rating: 4,
4464
4632
  num: 176,
@@ -4471,6 +4639,7 @@ exports.Abilities = {
4471
4639
  }
4472
4640
  }
4473
4641
  },
4642
+ flags: {},
4474
4643
  name: "Static",
4475
4644
  rating: 2,
4476
4645
  num: 9,
@@ -4479,6 +4648,7 @@ exports.Abilities = {
4479
4648
  onFlinch(pokemon) {
4480
4649
  this.boost({ spe: 1 });
4481
4650
  },
4651
+ flags: {},
4482
4652
  name: "Steadfast",
4483
4653
  rating: 1,
4484
4654
  num: 80,
@@ -4489,6 +4659,7 @@ exports.Abilities = {
4489
4659
  this.boost({ spe: 6 });
4490
4660
  }
4491
4661
  },
4662
+ flags: {},
4492
4663
  name: "Steam Engine",
4493
4664
  rating: 2,
4494
4665
  num: 243,
@@ -4508,6 +4679,7 @@ exports.Abilities = {
4508
4679
  return this.chainModify(1.5);
4509
4680
  }
4510
4681
  },
4682
+ flags: {},
4511
4683
  name: "Steelworker",
4512
4684
  rating: 3.5,
4513
4685
  num: 200,
@@ -4520,6 +4692,7 @@ exports.Abilities = {
4520
4692
  return this.chainModify(1.5);
4521
4693
  }
4522
4694
  },
4695
+ flags: {},
4523
4696
  name: "Steely Spirit",
4524
4697
  rating: 3.5,
4525
4698
  num: 252,
@@ -4541,6 +4714,7 @@ exports.Abilities = {
4541
4714
  });
4542
4715
  }
4543
4716
  },
4717
+ flags: {},
4544
4718
  name: "Stench",
4545
4719
  rating: 0.5,
4546
4720
  num: 1,
@@ -4556,7 +4730,7 @@ exports.Abilities = {
4556
4730
  return false;
4557
4731
  }
4558
4732
  },
4559
- isBreakable: true,
4733
+ flags: { breakable: 1 },
4560
4734
  name: "Sticky Hold",
4561
4735
  rating: 1.5,
4562
4736
  num: 60,
@@ -4583,7 +4757,7 @@ exports.Abilities = {
4583
4757
  return this.effectState.target;
4584
4758
  }
4585
4759
  },
4586
- isBreakable: true,
4760
+ flags: { breakable: 1 },
4587
4761
  name: "Storm Drain",
4588
4762
  rating: 3,
4589
4763
  num: 114,
@@ -4595,6 +4769,7 @@ exports.Abilities = {
4595
4769
  return this.chainModify(1.5);
4596
4770
  }
4597
4771
  },
4772
+ flags: {},
4598
4773
  name: "Strong Jaw",
4599
4774
  rating: 3.5,
4600
4775
  num: 173,
@@ -4613,7 +4788,7 @@ exports.Abilities = {
4613
4788
  return target.hp - 1;
4614
4789
  }
4615
4790
  },
4616
- isBreakable: true,
4791
+ flags: { breakable: 1 },
4617
4792
  name: "Sturdy",
4618
4793
  rating: 3,
4619
4794
  num: 5,
@@ -4624,7 +4799,7 @@ exports.Abilities = {
4624
4799
  this.add('-activate', pokemon, 'ability: Suction Cups');
4625
4800
  return null;
4626
4801
  },
4627
- isBreakable: true,
4802
+ flags: { breakable: 1 },
4628
4803
  name: "Suction Cups",
4629
4804
  rating: 1,
4630
4805
  num: 21,
@@ -4633,6 +4808,7 @@ exports.Abilities = {
4633
4808
  onModifyCritRatio(critRatio) {
4634
4809
  return critRatio + 1;
4635
4810
  },
4811
+ flags: {},
4636
4812
  name: "Super Luck",
4637
4813
  rating: 1.5,
4638
4814
  num: 105,
@@ -4657,6 +4833,7 @@ exports.Abilities = {
4657
4833
  }
4658
4834
  }
4659
4835
  },
4836
+ flags: {},
4660
4837
  name: "Supersweet Syrup",
4661
4838
  rating: 1.5,
4662
4839
  num: 306,
@@ -4681,6 +4858,7 @@ exports.Abilities = {
4681
4858
  return this.chainModify([powMod[this.effectState.fallen], 4096]);
4682
4859
  }
4683
4860
  },
4861
+ flags: {},
4684
4862
  name: "Supreme Overlord",
4685
4863
  rating: 4,
4686
4864
  num: 293,
@@ -4691,6 +4869,7 @@ exports.Abilities = {
4691
4869
  return this.chainModify(2);
4692
4870
  }
4693
4871
  },
4872
+ flags: {},
4694
4873
  name: "Surge Surfer",
4695
4874
  rating: 3,
4696
4875
  num: 207,
@@ -4710,12 +4889,12 @@ exports.Abilities = {
4710
4889
  return this.chainModify(1.5);
4711
4890
  }
4712
4891
  },
4892
+ flags: {},
4713
4893
  name: "Swarm",
4714
4894
  rating: 2,
4715
4895
  num: 68,
4716
4896
  },
4717
4897
  sweetveil: {
4718
- name: "Sweet Veil",
4719
4898
  onAllySetStatus(status, target, source, effect) {
4720
4899
  if (status.id === 'slp') {
4721
4900
  this.debug('Sweet Veil interrupts sleep');
@@ -4732,7 +4911,8 @@ exports.Abilities = {
4732
4911
  return null;
4733
4912
  }
4734
4913
  },
4735
- isBreakable: true,
4914
+ flags: { breakable: 1 },
4915
+ name: "Sweet Veil",
4736
4916
  rating: 2,
4737
4917
  num: 175,
4738
4918
  },
@@ -4742,6 +4922,7 @@ exports.Abilities = {
4742
4922
  return this.chainModify(2);
4743
4923
  }
4744
4924
  },
4925
+ flags: {},
4745
4926
  name: "Swift Swim",
4746
4927
  rating: 3,
4747
4928
  num: 33,
@@ -4761,6 +4942,7 @@ exports.Abilities = {
4761
4942
  }
4762
4943
  this.add('-activate', source, 'ability: Symbiosis', myItem, '[of] ' + pokemon);
4763
4944
  },
4945
+ flags: {},
4764
4946
  name: "Symbiosis",
4765
4947
  rating: 0,
4766
4948
  num: 180,
@@ -4778,6 +4960,7 @@ exports.Abilities = {
4778
4960
  // and show messages when activating against it.
4779
4961
  source.trySetStatus(status, target, { status: status.id, id: 'synchronize' });
4780
4962
  },
4963
+ flags: {},
4781
4964
  name: "Synchronize",
4782
4965
  rating: 2,
4783
4966
  num: 28,
@@ -4799,6 +4982,7 @@ exports.Abilities = {
4799
4982
  this.debug('Sword of Ruin Def drop');
4800
4983
  return this.chainModify(0.75);
4801
4984
  },
4985
+ flags: {},
4802
4986
  name: "Sword of Ruin",
4803
4987
  rating: 4.5,
4804
4988
  num: 285,
@@ -4820,6 +5004,7 @@ exports.Abilities = {
4820
5004
  this.debug('Tablets of Ruin Atk drop');
4821
5005
  return this.chainModify(0.75);
4822
5006
  },
5007
+ flags: {},
4823
5008
  name: "Tablets of Ruin",
4824
5009
  rating: 4.5,
4825
5010
  num: 284,
@@ -4834,7 +5019,7 @@ exports.Abilities = {
4834
5019
  return this.chainModify(0.5);
4835
5020
  }
4836
5021
  },
4837
- isBreakable: true,
5022
+ flags: { breakable: 1 },
4838
5023
  name: "Tangled Feet",
4839
5024
  rating: 1,
4840
5025
  num: 77,
@@ -4846,6 +5031,7 @@ exports.Abilities = {
4846
5031
  this.boost({ spe: -1 }, source, target, null, true);
4847
5032
  }
4848
5033
  },
5034
+ flags: {},
4849
5035
  name: "Tangling Hair",
4850
5036
  rating: 2,
4851
5037
  num: 221,
@@ -4860,6 +5046,7 @@ exports.Abilities = {
4860
5046
  return this.chainModify(1.5);
4861
5047
  }
4862
5048
  },
5049
+ flags: {},
4863
5050
  name: "Technician",
4864
5051
  rating: 3.5,
4865
5052
  num: 101,
@@ -4871,7 +5058,7 @@ exports.Abilities = {
4871
5058
  return null;
4872
5059
  }
4873
5060
  },
4874
- isBreakable: true,
5061
+ flags: { breakable: 1 },
4875
5062
  name: "Telepathy",
4876
5063
  rating: 0,
4877
5064
  num: 140,
@@ -4886,13 +5073,14 @@ exports.Abilities = {
4886
5073
  this.field.clearTerrain();
4887
5074
  }
4888
5075
  },
5076
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1 },
4889
5077
  name: "Teraform Zero",
4890
5078
  rating: 3,
4891
5079
  num: 309,
4892
5080
  },
4893
5081
  terashell: {
4894
5082
  onEffectiveness(typeMod, target, type, move) {
4895
- if (!target || target.species.name !== 'Terapagos-Terastal')
5083
+ if (!target || target.baseSpecies.name !== 'Terapagos-Terastal')
4896
5084
  return;
4897
5085
  if (this.effectState.resisted)
4898
5086
  return -1; // all hits of multi-hit move should be not very effective
@@ -4909,21 +5097,21 @@ exports.Abilities = {
4909
5097
  onAnyAfterMove() {
4910
5098
  this.effectState.resisted = false;
4911
5099
  },
4912
- isBreakable: true,
5100
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, breakable: 1 },
4913
5101
  name: "Tera Shell",
4914
5102
  rating: 3.5,
4915
5103
  num: 308,
4916
5104
  },
4917
5105
  terashift: {
4918
5106
  onPreStart(pokemon) {
4919
- if (pokemon.baseSpecies.baseSpecies !== 'Terapagos' || pokemon.transformed)
5107
+ if (pokemon.baseSpecies.baseSpecies !== 'Terapagos')
4920
5108
  return;
4921
5109
  if (pokemon.species.forme !== 'Terastal') {
4922
5110
  this.add('-activate', pokemon, 'ability: Tera Shift');
4923
5111
  pokemon.formeChange('Terapagos-Terastal', this.effect, true);
4924
5112
  }
4925
5113
  },
4926
- isPermanent: true,
5114
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1, notransform: 1 },
4927
5115
  name: "Tera Shift",
4928
5116
  rating: 3,
4929
5117
  num: 307,
@@ -4935,6 +5123,7 @@ exports.Abilities = {
4935
5123
  onModifyMove(move) {
4936
5124
  move.ignoreAbility = true;
4937
5125
  },
5126
+ flags: {},
4938
5127
  name: "Teravolt",
4939
5128
  rating: 3,
4940
5129
  num: 164,
@@ -4959,6 +5148,7 @@ exports.Abilities = {
4959
5148
  }
4960
5149
  return false;
4961
5150
  },
5151
+ flags: { breakable: 1 },
4962
5152
  name: "Thermal Exchange",
4963
5153
  rating: 2.5,
4964
5154
  num: 270,
@@ -4978,7 +5168,7 @@ exports.Abilities = {
4978
5168
  return this.chainModify(0.5);
4979
5169
  }
4980
5170
  },
4981
- isBreakable: true,
5171
+ flags: { breakable: 1 },
4982
5172
  name: "Thick Fat",
4983
5173
  rating: 3.5,
4984
5174
  num: 47,
@@ -4990,6 +5180,7 @@ exports.Abilities = {
4990
5180
  return this.chainModify(2);
4991
5181
  }
4992
5182
  },
5183
+ flags: {},
4993
5184
  name: "Tinted Lens",
4994
5185
  rating: 4,
4995
5186
  num: 110,
@@ -5009,6 +5200,7 @@ exports.Abilities = {
5009
5200
  return this.chainModify(1.5);
5010
5201
  }
5011
5202
  },
5203
+ flags: {},
5012
5204
  name: "Torrent",
5013
5205
  rating: 2,
5014
5206
  num: 67,
@@ -5020,6 +5212,7 @@ exports.Abilities = {
5020
5212
  return this.chainModify([5325, 4096]);
5021
5213
  }
5022
5214
  },
5215
+ flags: {},
5023
5216
  name: "Tough Claws",
5024
5217
  rating: 3.5,
5025
5218
  num: 181,
@@ -5031,6 +5224,7 @@ exports.Abilities = {
5031
5224
  return this.chainModify(1.5);
5032
5225
  }
5033
5226
  },
5227
+ flags: {},
5034
5228
  name: "Toxic Boost",
5035
5229
  rating: 3,
5036
5230
  num: 137,
@@ -5044,6 +5238,7 @@ exports.Abilities = {
5044
5238
  target.trySetStatus('tox', source);
5045
5239
  }
5046
5240
  },
5241
+ flags: {},
5047
5242
  name: "Toxic Chain",
5048
5243
  rating: 4.5,
5049
5244
  num: 305,
@@ -5057,6 +5252,7 @@ exports.Abilities = {
5057
5252
  side.addSideCondition('toxicspikes', target);
5058
5253
  }
5059
5254
  },
5255
+ flags: {},
5060
5256
  name: "Toxic Debris",
5061
5257
  rating: 3.5,
5062
5258
  num: 295,
@@ -5077,11 +5273,7 @@ exports.Abilities = {
5077
5273
  onUpdate(pokemon) {
5078
5274
  if (!pokemon.isStarted || this.effectState.gaveUp)
5079
5275
  return;
5080
- const additionalBannedAbilities = [
5081
- // Zen Mode included here for compatability with Gen 5-6
5082
- 'noability', 'commander', 'flowergift', 'forecast', 'hungerswitch', 'illusion', 'imposter', 'neutralizinggas', 'powerofalchemy', 'receiver', 'trace', 'zenmode',
5083
- ];
5084
- const possibleTargets = pokemon.adjacentFoes().filter(target => (!target.getAbility().isPermanent && !additionalBannedAbilities.includes(target.ability)));
5276
+ const possibleTargets = pokemon.adjacentFoes().filter(target => !target.getAbility().flags['notrace'] && target.ability !== 'noability');
5085
5277
  if (!possibleTargets.length)
5086
5278
  return;
5087
5279
  const target = this.sample(possibleTargets);
@@ -5090,6 +5282,7 @@ exports.Abilities = {
5090
5282
  this.add('-ability', pokemon, ability, '[from] ability: Trace', '[of] ' + target);
5091
5283
  }
5092
5284
  },
5285
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1 },
5093
5286
  name: "Trace",
5094
5287
  rating: 2.5,
5095
5288
  num: 36,
@@ -5109,6 +5302,7 @@ exports.Abilities = {
5109
5302
  return this.chainModify([5325, 4096]);
5110
5303
  }
5111
5304
  },
5305
+ flags: {},
5112
5306
  name: "Transistor",
5113
5307
  rating: 3.5,
5114
5308
  num: 262,
@@ -5118,6 +5312,7 @@ exports.Abilities = {
5118
5312
  if (move?.flags['heal'])
5119
5313
  return priority + 3;
5120
5314
  },
5315
+ flags: {},
5121
5316
  name: "Triage",
5122
5317
  rating: 3.5,
5123
5318
  num: 205,
@@ -5138,6 +5333,7 @@ exports.Abilities = {
5138
5333
  pokemon.addVolatile('truant');
5139
5334
  },
5140
5335
  condition: {},
5336
+ flags: {},
5141
5337
  name: "Truant",
5142
5338
  rating: -1,
5143
5339
  num: 54,
@@ -5149,12 +5345,12 @@ exports.Abilities = {
5149
5345
  onModifyMove(move) {
5150
5346
  move.ignoreAbility = true;
5151
5347
  },
5348
+ flags: {},
5152
5349
  name: "Turboblaze",
5153
5350
  rating: 3,
5154
5351
  num: 163,
5155
5352
  },
5156
5353
  unaware: {
5157
- name: "Unaware",
5158
5354
  onAnyModifyBoost(boosts, pokemon) {
5159
5355
  const unawareUser = this.effectState.target;
5160
5356
  if (unawareUser === pokemon)
@@ -5171,7 +5367,8 @@ exports.Abilities = {
5171
5367
  boosts['accuracy'] = 0;
5172
5368
  }
5173
5369
  },
5174
- isBreakable: true,
5370
+ flags: { breakable: 1 },
5371
+ name: "Unaware",
5175
5372
  rating: 4,
5176
5373
  num: 109,
5177
5374
  },
@@ -5194,6 +5391,7 @@ exports.Abilities = {
5194
5391
  }
5195
5392
  },
5196
5393
  },
5394
+ flags: {},
5197
5395
  name: "Unburden",
5198
5396
  rating: 3.5,
5199
5397
  num: 84,
@@ -5215,6 +5413,7 @@ exports.Abilities = {
5215
5413
  onFoeTryEatItem() {
5216
5414
  return !this.effectState.unnerved;
5217
5415
  },
5416
+ flags: {},
5218
5417
  name: "Unnerve",
5219
5418
  rating: 1,
5220
5419
  num: 127,
@@ -5224,6 +5423,7 @@ exports.Abilities = {
5224
5423
  if (move.flags['contact'])
5225
5424
  delete move.flags['protect'];
5226
5425
  },
5426
+ flags: {},
5227
5427
  name: "Unseen Fist",
5228
5428
  rating: 2,
5229
5429
  num: 260,
@@ -5245,6 +5445,7 @@ exports.Abilities = {
5245
5445
  this.debug('Vessel of Ruin SpA drop');
5246
5446
  return this.chainModify(0.75);
5247
5447
  },
5448
+ flags: {},
5248
5449
  name: "Vessel of Ruin",
5249
5450
  rating: 4.5,
5250
5451
  num: 284,
@@ -5256,6 +5457,7 @@ exports.Abilities = {
5256
5457
  return this.chainModify([4506, 4096]);
5257
5458
  }
5258
5459
  },
5460
+ flags: {},
5259
5461
  name: "Victory Star",
5260
5462
  rating: 2,
5261
5463
  num: 162,
@@ -5281,7 +5483,7 @@ exports.Abilities = {
5281
5483
  return null;
5282
5484
  }
5283
5485
  },
5284
- isBreakable: true,
5486
+ flags: { breakable: 1 },
5285
5487
  name: "Vital Spirit",
5286
5488
  rating: 1.5,
5287
5489
  num: 72,
@@ -5295,18 +5497,15 @@ exports.Abilities = {
5295
5497
  return null;
5296
5498
  }
5297
5499
  },
5298
- isBreakable: true,
5500
+ flags: { breakable: 1 },
5299
5501
  name: "Volt Absorb",
5300
5502
  rating: 3.5,
5301
5503
  num: 10,
5302
5504
  },
5303
5505
  wanderingspirit: {
5304
5506
  onDamagingHit(damage, target, source, move) {
5305
- const additionalBannedAbilities = ['commander', 'hungerswitch', 'illusion', 'neutralizinggas', 'wonderguard'];
5306
- if (source.getAbility().isPermanent || additionalBannedAbilities.includes(source.ability) ||
5307
- target.volatiles['dynamax']) {
5507
+ if (source.getAbility().flags['failskillswap'] || target.volatiles['dynamax'])
5308
5508
  return;
5309
- }
5310
5509
  if (this.checkMoveMakesContact(move, source, target)) {
5311
5510
  const targetCanBeSet = this.runEvent('SetAbility', target, source, this.effect, source.ability);
5312
5511
  if (!targetCanBeSet)
@@ -5323,6 +5522,7 @@ exports.Abilities = {
5323
5522
  target.setAbility(sourceAbility);
5324
5523
  }
5325
5524
  },
5525
+ flags: {},
5326
5526
  name: "Wandering Spirit",
5327
5527
  rating: 2.5,
5328
5528
  num: 254,
@@ -5336,7 +5536,7 @@ exports.Abilities = {
5336
5536
  return null;
5337
5537
  }
5338
5538
  },
5339
- isBreakable: true,
5539
+ flags: { breakable: 1 },
5340
5540
  name: "Water Absorb",
5341
5541
  rating: 3.5,
5342
5542
  num: 11,
@@ -5378,7 +5578,7 @@ exports.Abilities = {
5378
5578
  }
5379
5579
  return false;
5380
5580
  },
5381
- isBreakable: true,
5581
+ flags: { breakable: 1 },
5382
5582
  name: "Water Bubble",
5383
5583
  rating: 4.5,
5384
5584
  num: 199,
@@ -5389,6 +5589,7 @@ exports.Abilities = {
5389
5589
  this.boost({ def: 2 });
5390
5590
  }
5391
5591
  },
5592
+ flags: {},
5392
5593
  name: "Water Compaction",
5393
5594
  rating: 1.5,
5394
5595
  num: 195,
@@ -5408,7 +5609,7 @@ exports.Abilities = {
5408
5609
  }
5409
5610
  return false;
5410
5611
  },
5411
- isBreakable: true,
5612
+ flags: { breakable: 1 },
5412
5613
  name: "Water Veil",
5413
5614
  rating: 2,
5414
5615
  num: 41,
@@ -5419,6 +5620,7 @@ exports.Abilities = {
5419
5620
  this.boost({ def: -1, spe: 2 }, target, target);
5420
5621
  }
5421
5622
  },
5623
+ flags: {},
5422
5624
  name: "Weak Armor",
5423
5625
  rating: 1,
5424
5626
  num: 133,
@@ -5432,7 +5634,7 @@ exports.Abilities = {
5432
5634
  return null;
5433
5635
  }
5434
5636
  },
5435
- isBreakable: true,
5637
+ flags: { breakable: 1 },
5436
5638
  name: "Well-Baked Body",
5437
5639
  rating: 3.5,
5438
5640
  num: 273,
@@ -5453,7 +5655,7 @@ exports.Abilities = {
5453
5655
  this.add("-fail", target, "unboost", "[from] ability: White Smoke", "[of] " + target);
5454
5656
  }
5455
5657
  },
5456
- isBreakable: true,
5658
+ flags: { breakable: 1 },
5457
5659
  name: "White Smoke",
5458
5660
  rating: 2,
5459
5661
  num: 73,
@@ -5470,6 +5672,7 @@ exports.Abilities = {
5470
5672
  target.switchFlag = true;
5471
5673
  this.add('-activate', target, 'ability: Wimp Out');
5472
5674
  },
5675
+ flags: {},
5473
5676
  name: "Wimp Out",
5474
5677
  rating: 1,
5475
5678
  num: 193,
@@ -5487,6 +5690,7 @@ exports.Abilities = {
5487
5690
  pokemon.addVolatile('charge');
5488
5691
  }
5489
5692
  },
5693
+ flags: {},
5490
5694
  name: "Wind Power",
5491
5695
  rating: 1,
5492
5696
  num: 277,
@@ -5511,7 +5715,7 @@ exports.Abilities = {
5511
5715
  this.boost({ atk: 1 }, pokemon, pokemon);
5512
5716
  }
5513
5717
  },
5514
- isBreakable: true,
5718
+ flags: { breakable: 1 },
5515
5719
  name: "Wind Rider",
5516
5720
  rating: 3.5,
5517
5721
  // We do not want Brambleghast to get Infiltrator in Randbats
@@ -5534,7 +5738,7 @@ exports.Abilities = {
5534
5738
  return null;
5535
5739
  }
5536
5740
  },
5537
- isBreakable: true,
5741
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, failskillswap: 1, breakable: 1 },
5538
5742
  name: "Wonder Guard",
5539
5743
  rating: 5,
5540
5744
  num: 25,
@@ -5547,7 +5751,7 @@ exports.Abilities = {
5547
5751
  return 50;
5548
5752
  }
5549
5753
  },
5550
- isBreakable: true,
5754
+ flags: { breakable: 1 },
5551
5755
  name: "Wonder Skin",
5552
5756
  rating: 2,
5553
5757
  num: 147,
@@ -5592,14 +5796,14 @@ exports.Abilities = {
5592
5796
  }
5593
5797
  },
5594
5798
  },
5595
- isPermanent: true,
5799
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1 },
5596
5800
  name: "Zen Mode",
5597
5801
  rating: 0,
5598
5802
  num: 161,
5599
5803
  },
5600
5804
  zerotohero: {
5601
5805
  onSwitchOut(pokemon) {
5602
- if (pokemon.baseSpecies.baseSpecies !== 'Palafin' || pokemon.transformed)
5806
+ if (pokemon.baseSpecies.baseSpecies !== 'Palafin')
5603
5807
  return;
5604
5808
  if (pokemon.species.forme !== 'Hero') {
5605
5809
  pokemon.formeChange('Palafin-Hero', this.effect, true);
@@ -5612,14 +5816,14 @@ exports.Abilities = {
5612
5816
  if (!this.effectState.switchingIn)
5613
5817
  return;
5614
5818
  this.effectState.switchingIn = false;
5615
- if (pokemon.baseSpecies.baseSpecies !== 'Palafin' || pokemon.transformed)
5819
+ if (pokemon.baseSpecies.baseSpecies !== 'Palafin')
5616
5820
  return;
5617
5821
  if (!this.effectState.heroMessageDisplayed && pokemon.species.forme === 'Hero') {
5618
5822
  this.add('-activate', pokemon, 'ability: Zero to Hero');
5619
5823
  this.effectState.heroMessageDisplayed = true;
5620
5824
  }
5621
5825
  },
5622
- isPermanent: true,
5826
+ flags: { failroleplay: 1, noreceiver: 1, noentrain: 1, notrace: 1, failskillswap: 1, cantsuppress: 1, notransform: 1 },
5623
5827
  name: "Zero to Hero",
5624
5828
  rating: 5,
5625
5829
  num: 278,
@@ -5638,14 +5842,13 @@ exports.Abilities = {
5638
5842
  }
5639
5843
  },
5640
5844
  isNonstandard: "CAP",
5641
- isBreakable: true,
5845
+ flags: { breakable: 1 },
5642
5846
  name: "Mountaineer",
5643
5847
  rating: 3,
5644
5848
  num: -2,
5645
5849
  },
5646
5850
  rebound: {
5647
5851
  isNonstandard: "CAP",
5648
- name: "Rebound",
5649
5852
  onTryHitPriority: 1,
5650
5853
  onTryHit(target, source, move) {
5651
5854
  if (this.effectState.target.activeTurns)
@@ -5672,14 +5875,16 @@ exports.Abilities = {
5672
5875
  condition: {
5673
5876
  duration: 1,
5674
5877
  },
5675
- isBreakable: true,
5878
+ flags: { breakable: 1 },
5879
+ name: "Rebound",
5676
5880
  rating: 3,
5677
5881
  num: -3,
5678
5882
  },
5679
5883
  persistent: {
5680
5884
  isNonstandard: "CAP",
5681
- name: "Persistent",
5682
5885
  // implemented in the corresponding move
5886
+ flags: {},
5887
+ name: "Persistent",
5683
5888
  rating: 3,
5684
5889
  num: -4,
5685
5890
  },