merge up to date

This commit is contained in:
Lylian 2024-12-27 16:41:15 +01:00
commit 3c48bd0228
133 changed files with 8805 additions and 7405 deletions

624
CREDITS.md Normal file
View File

@ -0,0 +1,624 @@
# 🎵 Music
## BGM
- Pokémon Mystery Dungeon: Explorers of Sky
- Arata Iiyoshi
- Hideki Sakamoto
- Keisuke Ito
- Ken-ichi Saito
- Yoshihiro Maeda
- Pokémon Black/White
- Go Ichinose
- Hitomi Sato
- Shota Kageyama
- Pokémon Mystery Dungeon: Rescue Team DX
- Keisuke Ito
- Arata Iiyoshi
- Atsuhiro Ishizuna
- Pokémon HeartGold/SoulSilver
- Pokémon Black/White 2
- Pokémon X/Y
- Pokémon Omega Ruby/Alpha Sapphire
- Pokémon Sun/Moon
- Pokémon Ultra Sun/Ultra Moon
- Pokémon Sword/Shield
- Pokémon Legends: Arceus
- Pokémon Scarlet/Violet
- Firel (Custom Graveyard, Ice Cave, Laboratory, Metropolis, Plains, Power Plant, Seabed, Space, and Volcano biome music)
- Lmz (Custom Ancient Ruins, Jungle, and Lake biome music)
- Andr06 (Custom Forest, Slum and Sea biome music)
- _tresnoir
- unveiler
## Sound Effects
- Pokémon Emerald
- Pokémon Black/White
# 🎨 Art
## Backgrounds
- Squip (Paid Commissions)
- Contributions by Someonealive-QN
## UI
- GAMEFREAK
- LJ Birdman
## Pagefault Games Intro
- Spectremint
## Game Logo
- Gonstar (Paid Commission)
## Trainer Sprites
- GAMEFREAK (Pokémon Black/White 2, Pokémon Diamond/Pearl)
- kyledove
- Brumirage
- pkmn_realidea (Paid Commissions)
- IceJkai
- Leparagon
- wormhood
## Mystery Event Sprites
- chrysomelinae
- koda_want_to_sleep
- “🐺Kieran/YJ 🐍” rival_kieran aka thedreadedden
- ImperialSympathizer
- wormhood
- gerolau
- otterwatch
## Trainer Portraits
- pkmn_realidea (Paid Commissions)
## Pokémon Sprites and Animation
In addition to the lists below, please check [the PokéRogue wiki](https://wiki.pokerogue.net/credits:credits) for a more detailed list of Pokémon Sprite credits.
- GAMEFREAK (Pokémon Black/White 2)
- Smogon Sprite Project (Various Artists)
- Skyflyer
- Nolo33
- Ebaru
- EricLostie
- kiriaura
- Caruban
- Sopita_Yorita
- Azrita
- AshnixsLaw
- Hellfire0raptor
- RetroNC
- Franark122k
- OldSoulja
- PKMarioG
- ItsYugen
- lucasomi
- Pkm Sinfonia
- Poki Papillon
- Fleimer_
- bizcoeindoloro
- mangalos810
- selstar
### Static Sprites and Base Shiny Replacements Credits
- AMVictory
- Antiant
- Arhops
- arinoelle
- Arkeis
- aXl
- BananaToast
- Basic Vanillite
- BlackWhiteRobin
- Blaquaza
- Branflakes325
- Brylark
- Buna
- Bynine
- Corson
- Cynda
- “Diashi” diazhi
- Dleep
- doomchaos
- Espeon Scientist
- Farriella
- fishbowlsoul90
- “Follower” rulerofthesea11
- Galifia
- GeoisEvil
- G.E.Z.
- Glustora
- Harrie
- HealnDeal
- Hematite
- HM100
- Ice-cold Claws
- Involuntary Twitch
- “Jay” itsamejay
- KattenK
- KingOfThe-X-Roads
- KyleDove
- Kyleo
- Kyuzeth
- Larryturbo
- Layell
- Legitimate Username
- leParagon
- “LJ” lj_birdman
- Luigi Player
- Madmadness65
- Mega-Pokebattlerz
- Mintly
- mjco
- “Momo” sphinx_sage
- MrDollSteak
- MyMarshlands
- N-Kin
- Noscium
- “Nova” fabunova
- “Omniv” omniv
- paintseagull
- princessofmusic
- PumpkinPastel
- Quanyails
- RadicalCharizard
- RedRooster
- “♂ROMEO⚧” gerolau
- ruleroftheseas11
- SelenaArmorclaw
- “serif” serifaizawa
- Siiilver
- Sleet
- Snivy101
- Speed-X
- Sphex
- Spook
- Squip
- TeraVolt
- TheAetherPlayer
- TheCynicalPoet
- Tooni
- TrainerSplash
- Travis
- Turtleye
- Tyrell D. Barnes
- “Vari” \_vari\_
- Wobblebuns
- WolfPP
- WPS
- Wyverii
- “zan” smtif
- Zerudez
- Z-nogyroP
### Animated Sprites Credits
- Antiant
- arinoelle
- Blaquaza
- Claire Starsword
- Coyotango
- DanEx
- “Diashi” diazhi
- GalacticArtistMuffin
- G.E.Z.
- hexagonereal
- HM100
- Katten
- LeParagon
- localghost
- MallowOut
- mattiwarden
- “Momo” sphinx_sage
- N-Kin
- NoelleMBrooks
- Nyx
- “Omniv” omniv
- princessofmusic
- PumpkinPastel
- RadicalCharizard
- seleccion
- SelenaArmorclaw
- TheAetherPlayer
- Tinkatooni
- Typhlito
- uppa
- “Vari” \_vari\_
### Rare/Epic Shiny Variants Credits
- “Andr06” andr06
- “Appo” appo
- “Ashhawk” k_redacted
- “Auralite” _auralite
- “Awesome_Soul” awesome_soul
- “Bagon” bagonganda
- “Bibble” nuts_.
- “BloomOfWoods” bloomofwoods
- “Buge” buge
- “bun” bunove
- “bukie” bukie
- cameranian
- “Caramel” saltedcarriemel
- “Chocolate Niblets” choconibs
- “CKC” ckc_
- “ClawsHDi” clawshdi
- “Clown Princess” clown_princess
- “Cmac2173” cmac2173
- “Corsola” corsola_bandit
- “Criminon” criminon
- “Cryptican Gogoat Enthusiast” crypticanexe
- “Diashi” diazhi
- “deviant.daffodil, bug enthusiast” deviant.daffodil
- “DigitalVaporeon” digitalvaporeon
- dingosig
- “Eku” ekusas00
- “Elefante”
- “Esca” colossalsquid
- “Folf” folf.
- “Follower” ruleroftheseas11
- “Fontbane” fontbane
- “Gallow” gallowhound
- “Giojoe” giojoe10
- “Gonfold” gonfold
- greenninja757
- “Grassy_Storm” grassy_storm
- “GreenMegaMan” greenmegaman
- “GROWL” myflixer.to
- “guy claiming to work on a guide” 7thatlas
- “h. 🍄” letterh.
- “hamez” .hamez
- “Hanniel” hanniel.15
- “ImaginaryNeon” imaginaryneon
- “Jay” itsamejay
- “Jelke” jelke
- kalikimothy
- “🐺Kieran/YJ 🐍” rival_kieran aka thedreadedden
- “Koda” Koda_want_to_sleep
- “Lana” smogonian
- “LJ” lj_birdman
- “Long Girl” docamakesart
- “Lucky” luckyluckylucky
- “MissingNo.” clickonflareblitz
- “Momo” sphinx_sage
- monkehestman
- “Nexxus” nexxus_
- “Nik :3” realniktrustme
- “Nikolatsu”
- “nora” ora.n
- “NOVA” fabunova
- officerporkchops
- “Omniv” omniv
- “Otterwatch” otterwatch_
- “Pandoraz” pandoraz
- “Papa Pepsm An” papapepsman
- “Penguin” peng06
- “Prodigy” lorekeeperprodigy
- “Purpenigma” purpenigma
- “Rage” ragerevival
- “♂ROMEO⚧” gerolau
- “Sagrell D'Arcadia” coffeerequired
- “serif” serifaizawa
- “SillyTopplingGoose” sillytopplinggoose
- “Splash Damage” splashceles
- “Sweg1b01” sweg1b01
- “SyntheGrim” synthegrim
- “TaMenace” tamariontherestless
- “TheTRUEgge” thetruegge
- “Thorn” crownofthorns
- “Togepi” togepimax
- “Toopy” .toopy
- “Tristan” tristan.w
- “Umbreon” umbreon\_.\_
- “Vari” \_vari\_
- “Waasephi”
- wormhood
- “Yep, it's Caio” yepitscaio
- “Ymri” ymri
- “zaccie” zaccie
- “zan” smtif
## Move Animations
- Pokémon Reborn
# ⚖️ Balance
## Balance Team
- damocleas
- Blitzy aka Kazapple
- Cynthia_calliope
- Esca
- Fontbane
- Plasto
- Sethcurry
- Starkrieg
## Past Members
- Swizzo
- Zaccie
## Past Contributors
- chrysomelinae (Mystery Events)
- AsdarDevelops (Mystery Events)
# 💻 Development
## Server Owner/Administrator
- pancakes aka patapancakes
## Senior Developers
- Walker
- NightKev
- Moka
- Temp aka Tempo-anon
- Madmadness65
## Developers
- CodeTappert
- flx-sta
- innerthunder
- frutescens
- Opaquer
- SN34KZ
- Swain aka torranx
## Junior Developers
- KimJeongSun
- ImperialSympathizer
## Bug/Issue Managers
- Snailman
- Daleks
- Lily
- PigeonBar
## Other Code Contributors
- Admiral-Billy
- allen925
- arColm
- Arxalc
- AsdarDevelops
- bennybroseph
- Brain Frog
- Corrade
- Dakurei
- DustinLin
- ElizaAlex
- EmberCM
- EmoUsedHM01
- EvasiveAce
- Fontbane
- francktrouillez
- FredeX
- geeilhan
- Greenlamp
- happinyz
- hayuna
- InfernoVulpix
- j-diefenbach
- jaimefd
- JakubHanko
- JonStudders
- karl-police
- lucfd
- Lugiadrien
- madibye
- mattrossdev
- mcmontag
- meepen
- Mewtwo2387
- muscode
- Neverblade
- NxKarim
- okimin
- OrangeRed
- PigeonBar
- PrabbyDD
- prateau
- prime-dialga
- PyGaVS
- rationality6
- RedstonewolfX
- ReneGV
- rnicar245
- Sam aka Flashfyre (initial developer, started PokéRogue)
- schmidtc1
- shayebeadling
- sirzento
- snoozbuster
- sodaMelon
- td76099
- Vassiat
- Xiaphear
- zaccie
- zacharied
- Zé Ricardo
# 🌎 Translation
## In-Game Translators
### 🇩🇪 German (de)
- CodeTappert
### 🇪🇸 Spanish (es-ES)
- Dan Stevenson
- Javi
- Lily Alterni
- Qyxgames
### 🇫🇷 French (fr)
- Lugiadrien
### 🇮🇹 Italian (it)
- Nicus
### 🇯🇵 Japanese (ja)
- 6mozuke9
- Chapybara
- PeachFresca
### 🇰🇷 Korean (ko)
- Enoch
- KimJeongSun
- Returntoice
- sodamelon
### 🇧🇷 Portuguese (pt-BR)
- Zé Ricardo
### 🇨🇳 Chinese (zh-CN)
- dddsenic
- mercurius
- VittorioVeneto
- Yonmaru
### 🇹🇼 Chinese (zh-TW)
- mercurius
- Seagull
### Past contributors
- Asdar (es-ES)
- Rafa (es-ES)
- GINK-SS (ko)
- prostagma (pt-BR)
- Ei (zh-TW)
## Wiki Translators
### 🇪🇸 Spanish (es-ES)
- victorcooler
### 🇫🇷 French (fr)
- Evan
- Mitsue
- Papier
- Sangara
- Voltarix
### 🇮🇹 Italian (it)
- Purce
- T-reds
### 🇰🇷 Korean (ko)
- LeKaaN
- Returntoice
- sodamelon
### 🇵🇱 Polish (pl)
- Talo
### 🇧🇷 Portuguese (pt-BR)
- Beast
- Sushi
- Zé Ricardo
### 🇨🇳 Chinese (zh-CN)
- jw-0-
### Past contributors
- Dietaube (de)
- Gnorpelltroll (de)
- xRegix (de)
- Broly Ikari (fr)
- Leo Edgar_Zimmer (fr)
- Telor (fr)
- dorri (ko)
- Little Moder_eldenring (ko)
- Andy (zh-CN)
- Black Feather (zh-CN)
- itschili (zh-CN)
- RimKnight (zh-CN)
- Yubari (zh-CN)
## 🇺🇸 English Proofreaders
- Cheyu
- Faust
- HaywiredUp
- Irridescence
- Ke'ahi
- Louie
- Nully
- PeD
- The Programmer
### Past contributors
- I...
# 📰 Wiki
## Wiki Head
- H.A.R.V.
## Wiki Lead
- Sangara
- Zac
- Smew
- Brain Frog
- Hannah
## Editor
- Prodigy
- Akuma
- Dan Gioia
- Shimizoki
- Stave
- NalysArbur
- Ceimir
- Solanum Tuberosum
- Pom
## Artist
- dub
- SmashMania
- Wren
- Lugiadrien
## Contributor
- Daleks <3
- Inferno Vulpix
- Embri
- Nekod
- P0kemonY
- Scoom
- BlueVaron
# ☎️ Discord
## Head Moderator
- leah
## Senior Moderators
- Solanum Tuberosum
- Madmadness65
- Necrowmancer
- lana
## Moderators
- Sethcurry
## Junior Moderators
- chacolah
- ChaosGrimmon
- Cynthia
- Kat
- lyn
- Pom
# ✨ Special Thanks
## Reddit Moderators
- TheZigglez
- Vicksin
- Sapphire
- Javi
- roi
## External Tools
- Ydarissep (creator of the now defunct "Yda's Dex")
- Admiral-Billy (Offline App - Desktop)
- Red aka StonedModder (iOS App)

View File

@ -37,93 +37,6 @@ For detailed guidelines on documenting your code, refer to the [comments.md](./d
Check out [Github Issues](https://github.com/pagefaultgames/pokerogue/issues) to see how can you help us! Check out [Github Issues](https://github.com/pagefaultgames/pokerogue/issues) to see how can you help us!
# 📝 Credits # 📝 Credits
> If this project contains assets you have produced and you do not see your name here, **please** reach out. > If this project contains assets you have produced and you do not see your name, **please** reach out, either [here on GitHub](https://github.com/pagefaultgames/pokerogue/issues/new) or via [Discord](https://discord.gg/pokerogue).
### 🎵 BGM Thank you to all the wonderful people that have contributed to the PokéRogue project! You can find the credits [here](./CREDITS.md).
- Pokémon Mystery Dungeon: Explorers of Sky
- Arata Iiyoshi
- Hideki Sakamoto
- Keisuke Ito
- Ken-ichi Saito
- Yoshihiro Maeda
- Pokémon Black/White
- Go Ichinose
- Hitomi Sato
- Shota Kageyama
- Pokémon Mystery Dungeon: Rescue Team DX
- Keisuke Ito
- Arata Iiyoshi
- Atsuhiro Ishizuna
- Pokémon HeartGold/SoulSilver
- Pokémon Black/White 2
- Pokémon X/Y
- Pokémon Omega Ruby/Alpha Sapphire
- Pokémon Sun/Moon
- Pokémon Ultra Sun/Ultra Moon
- Pokémon Sword/Shield
- Pokémon Legends: Arceus
- Pokémon Scarlet/Violet
- Firel (Custom Ice Cave, Laboratory, Metropolis, Plains, Power Plant, Seabed, Space, and Volcano biome music)
- Lmz (Custom Ancient Ruins, Jungle, and Lake biome music)
- Andr06 (Custom Slum and Sea biome music)
### 🎵 Sound Effects
- Pokémon Emerald
- Pokémon Black/White
### 🎨 Backgrounds
- Squip (Paid Commissions)
- Contributions by Someonealive-QN
### 🎨 UI
- GAMEFREAK
- LJ Birdman
### 🎨 Pagefault Games Intro
- Spectremint
### 🎨 Game Logo
- Gonstar (Paid Commission)
### 🎨 Trainer Sprites
- GAMEFREAK (Pokémon Black/White 2, Pokémon Diamond/Pearl)
- kyledove
- Brumirage
- pkmn_realidea (Paid Commissions)
- IceJkai
### 🎨 Trainer Portraits
- pkmn_realidea (Paid Commissions)
### 🎨 Pokemon Sprites and Animation
- GAMEFREAK (Pokémon Black/White 2)
- Smogon Sprite Project (Various Artists)
- Skyflyer
- Nolo33
- Ebaru
- EricLostie
- KingOfThe-X-Roads
- kiriaura
- Caruban
- Sopita_Yorita
- Azrita
- AshnixsLaw
- Hellfire0raptor
- RetroNC
- Franark122k
- OldSoulja
- PKMarioG
- ItsYugen
- lucasomi
- Pkm Sinfonia
- Poki Papillon
- Fleimer_
- bizcoeindoloro
- mangalos810
- Involuntary-Twitch
- selstar
- koda_want_to_sleep
- thedreadedden
### 🎨 Move Animations
- Pokémon Reborn

91
package-lock.json generated
View File

@ -1,12 +1,12 @@
{ {
"name": "pokemon-rogue-battle", "name": "pokemon-rogue-battle",
"version": "1.2.2", "version": "1.4.1",
"lockfileVersion": 3, "lockfileVersion": 3,
"requires": true, "requires": true,
"packages": { "packages": {
"": { "": {
"name": "pokemon-rogue-battle", "name": "pokemon-rogue-battle",
"version": "1.2.2", "version": "1.4.1",
"hasInstallScript": true, "hasInstallScript": true,
"dependencies": { "dependencies": {
"@material/material-color-utilities": "^0.2.7", "@material/material-color-utilities": "^0.2.7",
@ -16,6 +16,7 @@
"i18next-http-backend": "^2.6.1", "i18next-http-backend": "^2.6.1",
"i18next-korean-postposition-processor": "^1.0.0", "i18next-korean-postposition-processor": "^1.0.0",
"json-stable-stringify": "^1.1.0", "json-stable-stringify": "^1.1.0",
"jszip": "^3.10.1",
"phaser": "^3.70.0", "phaser": "^3.70.0",
"phaser3-rex-plugins": "^1.1.84" "phaser3-rex-plugins": "^1.1.84"
}, },
@ -2723,6 +2724,11 @@
"node": ">= 0.6" "node": ">= 0.6"
} }
}, },
"node_modules/core-util-is": {
"version": "1.0.3",
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz",
"integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ=="
},
"node_modules/cross-fetch": { "node_modules/cross-fetch": {
"version": "4.0.0", "version": "4.0.0",
"resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-4.0.0.tgz", "resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-4.0.0.tgz",
@ -4045,6 +4051,11 @@
"node": ">= 4" "node": ">= 4"
} }
}, },
"node_modules/immediate": {
"version": "3.0.6",
"resolved": "https://registry.npmjs.org/immediate/-/immediate-3.0.6.tgz",
"integrity": "sha512-XXOFtyqDjNDAQxVfYxuF7g9Il/IbWmmlQg2MYKOH8ExIT1qg6xc4zyS3HaEEATgs1btfzxq15ciUiY7gjSXRGQ=="
},
"node_modules/import-fresh": { "node_modules/import-fresh": {
"version": "3.3.0", "version": "3.3.0",
"resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz",
@ -4072,6 +4083,11 @@
"node": ">=0.8.19" "node": ">=0.8.19"
} }
}, },
"node_modules/inherits": {
"version": "2.0.4",
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
"integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="
},
"node_modules/ini": { "node_modules/ini": {
"version": "4.1.1", "version": "4.1.1",
"resolved": "https://registry.npmjs.org/ini/-/ini-4.1.1.tgz", "resolved": "https://registry.npmjs.org/ini/-/ini-4.1.1.tgz",
@ -4481,6 +4497,17 @@
"url": "https://github.com/sponsors/ljharb" "url": "https://github.com/sponsors/ljharb"
} }
}, },
"node_modules/jszip": {
"version": "3.10.1",
"resolved": "https://registry.npmjs.org/jszip/-/jszip-3.10.1.tgz",
"integrity": "sha512-xXDvecyTpGLrqFrvkrUSoxxfJI5AH7U8zxxtVclpsUtMCq4JQ290LY8AW5c7Ggnr/Y/oK+bQMbqK2qmtk3pN4g==",
"dependencies": {
"lie": "~3.3.0",
"pako": "~1.0.2",
"readable-stream": "~2.3.6",
"setimmediate": "^1.0.5"
}
},
"node_modules/keyv": { "node_modules/keyv": {
"version": "4.5.4", "version": "4.5.4",
"resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz",
@ -4648,6 +4675,14 @@
"node": ">= 0.8.0" "node": ">= 0.8.0"
} }
}, },
"node_modules/lie": {
"version": "3.3.0",
"resolved": "https://registry.npmjs.org/lie/-/lie-3.3.0.tgz",
"integrity": "sha512-UaiMJzeWRlEujzAuw5LokY1L5ecNQYZKfmyZ9L7wDHb/p5etKaxXhohBcrw0EYby+G/NA52vRSN4N39dxHAIwQ==",
"dependencies": {
"immediate": "~3.0.5"
}
},
"node_modules/linkify-it": { "node_modules/linkify-it": {
"version": "5.0.0", "version": "5.0.0",
"resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz", "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz",
@ -5237,6 +5272,11 @@
"dev": true, "dev": true,
"license": "BlueOak-1.0.0" "license": "BlueOak-1.0.0"
}, },
"node_modules/pako": {
"version": "1.0.11",
"resolved": "https://registry.npmjs.org/pako/-/pako-1.0.11.tgz",
"integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw=="
},
"node_modules/papaparse": { "node_modules/papaparse": {
"version": "5.4.1", "version": "5.4.1",
"resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.4.1.tgz", "resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.4.1.tgz",
@ -5485,6 +5525,11 @@
"node": ">= 0.8.0" "node": ">= 0.8.0"
} }
}, },
"node_modules/process-nextick-args": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz",
"integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag=="
},
"node_modules/prompts": { "node_modules/prompts": {
"version": "2.4.2", "version": "2.4.2",
"resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz",
@ -5551,6 +5596,25 @@
} }
] ]
}, },
"node_modules/readable-stream": {
"version": "2.3.8",
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz",
"integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==",
"dependencies": {
"core-util-is": "~1.0.0",
"inherits": "~2.0.3",
"isarray": "~1.0.0",
"process-nextick-args": "~2.0.0",
"safe-buffer": "~5.1.1",
"string_decoder": "~1.1.1",
"util-deprecate": "~1.0.1"
}
},
"node_modules/readable-stream/node_modules/isarray": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
"integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ=="
},
"node_modules/rechoir": { "node_modules/rechoir": {
"version": "0.8.0", "version": "0.8.0",
"resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.8.0.tgz", "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.8.0.tgz",
@ -5741,6 +5805,11 @@
"tslib": "^2.1.0" "tslib": "^2.1.0"
} }
}, },
"node_modules/safe-buffer": {
"version": "5.1.2",
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz",
"integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g=="
},
"node_modules/safe-regex": { "node_modules/safe-regex": {
"version": "2.1.1", "version": "2.1.1",
"resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-2.1.1.tgz", "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-2.1.1.tgz",
@ -5800,6 +5869,11 @@
"node": ">= 0.4" "node": ">= 0.4"
} }
}, },
"node_modules/setimmediate": {
"version": "1.0.5",
"resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz",
"integrity": "sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA=="
},
"node_modules/shebang-command": { "node_modules/shebang-command": {
"version": "2.0.0", "version": "2.0.0",
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
@ -5917,6 +5991,14 @@
"dev": true, "dev": true,
"license": "MIT" "license": "MIT"
}, },
"node_modules/string_decoder": {
"version": "1.1.1",
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz",
"integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==",
"dependencies": {
"safe-buffer": "~5.1.0"
}
},
"node_modules/string-width": { "node_modules/string-width": {
"version": "5.1.2", "version": "5.1.2",
"resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz",
@ -6473,6 +6555,11 @@
"requires-port": "^1.0.0" "requires-port": "^1.0.0"
} }
}, },
"node_modules/util-deprecate": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
"integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="
},
"node_modules/vite": { "node_modules/vite": {
"version": "5.4.8", "version": "5.4.8",
"resolved": "https://registry.npmjs.org/vite/-/vite-5.4.8.tgz", "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.8.tgz",

View File

@ -1,7 +1,7 @@
{ {
"name": "pokemon-rogue-battle", "name": "pokemon-rogue-battle",
"private": true, "private": true,
"version": "1.2.2", "version": "1.4.1",
"type": "module", "type": "module",
"scripts": { "scripts": {
"start": "vite", "start": "vite",
@ -55,6 +55,7 @@
"i18next-http-backend": "^2.6.1", "i18next-http-backend": "^2.6.1",
"i18next-korean-postposition-processor": "^1.0.0", "i18next-korean-postposition-processor": "^1.0.0",
"json-stable-stringify": "^1.1.0", "json-stable-stringify": "^1.1.0",
"jszip": "^3.10.1",
"phaser": "^3.70.0", "phaser": "^3.70.0",
"phaser3-rex-plugins": "^1.1.84" "phaser3-rex-plugins": "^1.1.84"
}, },

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.0 KiB

After

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 34 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 32 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 35 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 32 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.4 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

View File

@ -1,776 +1,299 @@
{ { "frames": [
"textures": [
{
"image": "47.png",
"format": "RGBA8888",
"size": {
"w": 230,
"h": 230
},
"scale": 1,
"frames": [
{
"filename": "0009.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 12,
"w": 56,
"h": 49
},
"frame": {
"x": 0,
"y": 0,
"w": 56,
"h": 49
}
},
{
"filename": "0010.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 12,
"w": 56,
"h": 49
},
"frame": {
"x": 0,
"y": 0,
"w": 56,
"h": 49
}
},
{
"filename": "0027.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 12,
"w": 62,
"h": 51
},
"frame": {
"x": 56,
"y": 0,
"w": 62,
"h": 51
}
},
{
"filename": "0028.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 12,
"w": 62,
"h": 51
},
"frame": {
"x": 56,
"y": 0,
"w": 62,
"h": 51
}
},
{
"filename": "0007.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 8,
"w": 55,
"h": 53
},
"frame": {
"x": 118,
"y": 0,
"w": 55,
"h": 53
}
},
{
"filename": "0008.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 8,
"w": 55,
"h": 53
},
"frame": {
"x": 118,
"y": 0,
"w": 55,
"h": 53
}
},
{
"filename": "0011.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 7,
"w": 55,
"h": 54
},
"frame": {
"x": 173,
"y": 0,
"w": 55,
"h": 54
}
},
{
"filename": "0012.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 7,
"w": 55,
"h": 54
},
"frame": {
"x": 173,
"y": 0,
"w": 55,
"h": 54
}
},
{
"filename": "0005.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 5,
"w": 53,
"h": 56
},
"frame": {
"x": 0,
"y": 49,
"w": 53,
"h": 56
}
},
{
"filename": "0006.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 5,
"w": 53,
"h": 56
},
"frame": {
"x": 0,
"y": 49,
"w": 53,
"h": 56
}
},
{
"filename": "0025.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 8,
"w": 62,
"h": 55
},
"frame": {
"x": 53,
"y": 51,
"w": 62,
"h": 55
}
},
{
"filename": "0026.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 8,
"w": 62,
"h": 55
},
"frame": {
"x": 53,
"y": 51,
"w": 62,
"h": 55
}
},
{
"filename": "0013.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 4,
"w": 53,
"h": 57
},
"frame": {
"x": 115,
"y": 53,
"w": 53,
"h": 57
}
},
{
"filename": "0014.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 4,
"w": 53,
"h": 57
},
"frame": {
"x": 115,
"y": 53,
"w": 53,
"h": 57
}
},
{
"filename": "0029.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 7,
"w": 62,
"h": 56
},
"frame": {
"x": 168,
"y": 54,
"w": 62,
"h": 56
}
},
{
"filename": "0030.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 7,
"w": 62,
"h": 56
},
"frame": {
"x": 168,
"y": 54,
"w": 62,
"h": 56
}
},
{
"filename": "0023.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 5,
"w": 61,
"h": 58
},
"frame": {
"x": 0,
"y": 106,
"w": 61,
"h": 58
}
},
{
"filename": "0024.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 5,
"w": 61,
"h": 58
},
"frame": {
"x": 0,
"y": 106,
"w": 61,
"h": 58
}
},
{
"filename": "0003.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 61,
"y": 106,
"w": 54,
"h": 59
}
},
{
"filename": "0004.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 61,
"y": 106,
"w": 54,
"h": 59
}
},
{ {
"filename": "0001.png", "filename": "0001.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0002.png", "filename": "0002.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0019.png", "filename": "0003.png",
"frame": { "x": 166, "y": 114, "w": 52, "h": 56 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 56 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0020.png", "filename": "0004.png",
"frame": { "x": 166, "y": 114, "w": 52, "h": 56 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 56 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 2, "filename": "0005.png",
"y": 2, "frame": { "x": 0, "y": 169, "w": 51, "h": 54 },
"w": 57, "rotated": false,
"h": 59 "trimmed": true,
"spriteSourceSize": { "x": 11, "y": 7, "w": 51, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 115, "filename": "0006.png",
"y": 110, "frame": { "x": 0, "y": 169, "w": 51, "h": 54 },
"w": 57, "rotated": false,
"h": 59 "trimmed": true,
} "spriteSourceSize": { "x": 11, "y": 7, "w": 51, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0007.png",
"frame": { "x": 104, "y": 166, "w": 53, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 9, "w": 53, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0008.png",
"frame": { "x": 104, "y": 166, "w": 53, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 9, "w": 53, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0009.png",
"frame": { "x": 157, "y": 170, "w": 55, "h": 49 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 9, "y": 12, "w": 55, "h": 49 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0010.png",
"frame": { "x": 157, "y": 170, "w": 55, "h": 49 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 9, "y": 12, "w": 55, "h": 49 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0011.png",
"frame": { "x": 0, "y": 115, "w": 53, "h": 54 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 8, "w": 53, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0012.png",
"frame": { "x": 0, "y": 115, "w": 53, "h": 54 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 8, "w": 53, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0013.png",
"frame": { "x": 53, "y": 116, "w": 51, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 11, "y": 6, "w": 51, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0014.png",
"frame": { "x": 53, "y": 116, "w": 51, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 11, "y": 6, "w": 51, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
}, },
{ {
"filename": "0015.png", "filename": "0015.png",
"frame": { "x": 114, "y": 109, "w": 52, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 172,
"y": 110,
"w": 54,
"h": 59
}
}, },
{ {
"filename": "0016.png", "filename": "0016.png",
"frame": { "x": 114, "y": 109, "w": 52, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 172,
"y": 110,
"w": 54,
"h": 59
}
},
{
"filename": "0031.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 4,
"w": 61,
"h": 59
},
"frame": {
"x": 0,
"y": 164,
"w": 61,
"h": 59
}
},
{
"filename": "0032.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 4,
"w": 61,
"h": 59
},
"frame": {
"x": 0,
"y": 164,
"w": 61,
"h": 59
}
}, },
{ {
"filename": "0017.png", "filename": "0017.png",
"frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0018.png", "filename": "0018.png",
"frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0035.png", "filename": "0019.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0036.png", "filename": "0020.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0021.png", "filename": "0021.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 2,
"w": 60,
"h": 61
},
"frame": {
"x": 118,
"y": 169,
"w": 60,
"h": 61
}
}, },
{ {
"filename": "0022.png", "filename": "0022.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 0, "filename": "0023.png",
"y": 2, "frame": { "x": 119, "y": 0, "w": 59, "h": 57 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
"spriteSourceSize": { "x": 3, "y": 7, "w": 59, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 118, "filename": "0024.png",
"y": 169, "frame": { "x": 119, "y": 0, "w": 59, "h": 57 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
} "spriteSourceSize": { "x": 3, "y": 7, "w": 59, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0025.png",
"frame": { "x": 178, "y": 0, "w": 60, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 9, "w": 60, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0026.png",
"frame": { "x": 178, "y": 0, "w": 60, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 9, "w": 60, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0027.png",
"frame": { "x": 114, "y": 57, "w": 62, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 2, "y": 12, "w": 62, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0028.png",
"frame": { "x": 114, "y": 57, "w": 62, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 2, "y": 12, "w": 62, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0029.png",
"frame": { "x": 59, "y": 0, "w": 60, "h": 57 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 8, "w": 60, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0030.png",
"frame": { "x": 59, "y": 0, "w": 60, "h": 57 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 8, "w": 60, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0031.png",
"frame": { "x": 0, "y": 0, "w": 59, "h": 58 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 6, "w": 59, "h": 58 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0032.png",
"frame": { "x": 0, "y": 0, "w": 59, "h": 58 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 6, "w": 59, "h": 58 },
"sourceSize": { "w": 65, "h": 65 }
}, },
{ {
"filename": "0033.png", "filename": "0033.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 2,
"w": 60,
"h": 61
},
"frame": {
"x": 118,
"y": 169,
"w": 60,
"h": 61
}
}, },
{ {
"filename": "0034.png", "filename": "0034.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 0, "filename": "0035.png",
"y": 2, "frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
"spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 118, "filename": "0036.png",
"y": 169, "frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
} "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
} "sourceSize": { "w": 65, "h": 65 }
]
} }
], ],
"meta": { "meta": {
"app": "https://www.codeandweb.com/texturepacker", "app": "https://www.aseprite.org/",
"version": "3.0", "version": "1.3.8.1-x64",
"smartupdate": "$TexturePacker:SmartUpdate:b28fe643197bcc1def0e0ac2ba9f4e67:516d08c8e1ff13b49a109b082ef12860:fe45e2d628a6cef0908f7b82468c8798$" "image": "47.png",
"format": "I8",
"size": { "w": 238, "h": 223 },
"scale": "1"
} }
} }

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.9 KiB

After

Width:  |  Height:  |  Size: 5.2 KiB

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.4 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

View File

@ -1,776 +1,299 @@
{ { "frames": [
"textures": [
{
"image": "47.png",
"format": "RGBA8888",
"size": {
"w": 230,
"h": 230
},
"scale": 1,
"frames": [
{
"filename": "0009.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 12,
"w": 56,
"h": 49
},
"frame": {
"x": 0,
"y": 0,
"w": 56,
"h": 49
}
},
{
"filename": "0010.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 12,
"w": 56,
"h": 49
},
"frame": {
"x": 0,
"y": 0,
"w": 56,
"h": 49
}
},
{
"filename": "0027.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 12,
"w": 62,
"h": 51
},
"frame": {
"x": 56,
"y": 0,
"w": 62,
"h": 51
}
},
{
"filename": "0028.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 12,
"w": 62,
"h": 51
},
"frame": {
"x": 56,
"y": 0,
"w": 62,
"h": 51
}
},
{
"filename": "0007.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 8,
"w": 55,
"h": 53
},
"frame": {
"x": 118,
"y": 0,
"w": 55,
"h": 53
}
},
{
"filename": "0008.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 8,
"w": 55,
"h": 53
},
"frame": {
"x": 118,
"y": 0,
"w": 55,
"h": 53
}
},
{
"filename": "0011.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 7,
"w": 55,
"h": 54
},
"frame": {
"x": 173,
"y": 0,
"w": 55,
"h": 54
}
},
{
"filename": "0012.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 7,
"y": 7,
"w": 55,
"h": 54
},
"frame": {
"x": 173,
"y": 0,
"w": 55,
"h": 54
}
},
{
"filename": "0005.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 5,
"w": 53,
"h": 56
},
"frame": {
"x": 0,
"y": 49,
"w": 53,
"h": 56
}
},
{
"filename": "0006.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 5,
"w": 53,
"h": 56
},
"frame": {
"x": 0,
"y": 49,
"w": 53,
"h": 56
}
},
{
"filename": "0025.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 8,
"w": 62,
"h": 55
},
"frame": {
"x": 53,
"y": 51,
"w": 62,
"h": 55
}
},
{
"filename": "0026.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 8,
"w": 62,
"h": 55
},
"frame": {
"x": 53,
"y": 51,
"w": 62,
"h": 55
}
},
{
"filename": "0013.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 4,
"w": 53,
"h": 57
},
"frame": {
"x": 115,
"y": 53,
"w": 53,
"h": 57
}
},
{
"filename": "0014.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 8,
"y": 4,
"w": 53,
"h": 57
},
"frame": {
"x": 115,
"y": 53,
"w": 53,
"h": 57
}
},
{
"filename": "0029.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 7,
"w": 62,
"h": 56
},
"frame": {
"x": 168,
"y": 54,
"w": 62,
"h": 56
}
},
{
"filename": "0030.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 7,
"w": 62,
"h": 56
},
"frame": {
"x": 168,
"y": 54,
"w": 62,
"h": 56
}
},
{
"filename": "0023.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 5,
"w": 61,
"h": 58
},
"frame": {
"x": 0,
"y": 106,
"w": 61,
"h": 58
}
},
{
"filename": "0024.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 5,
"w": 61,
"h": 58
},
"frame": {
"x": 0,
"y": 106,
"w": 61,
"h": 58
}
},
{
"filename": "0003.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 61,
"y": 106,
"w": 54,
"h": 59
}
},
{
"filename": "0004.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 61,
"y": 106,
"w": 54,
"h": 59
}
},
{ {
"filename": "0001.png", "filename": "0001.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0002.png", "filename": "0002.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0019.png", "filename": "0003.png",
"frame": { "x": 166, "y": 114, "w": 52, "h": 56 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 56 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 2,
"w": 57,
"h": 59
},
"frame": {
"x": 115,
"y": 110,
"w": 57,
"h": 59
}
}, },
{ {
"filename": "0020.png", "filename": "0004.png",
"frame": { "x": 166, "y": 114, "w": 52, "h": 56 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 56 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 2, "filename": "0005.png",
"y": 2, "frame": { "x": 0, "y": 169, "w": 51, "h": 54 },
"w": 57, "rotated": false,
"h": 59 "trimmed": true,
"spriteSourceSize": { "x": 11, "y": 7, "w": 51, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 115, "filename": "0006.png",
"y": 110, "frame": { "x": 0, "y": 169, "w": 51, "h": 54 },
"w": 57, "rotated": false,
"h": 59 "trimmed": true,
} "spriteSourceSize": { "x": 11, "y": 7, "w": 51, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0007.png",
"frame": { "x": 104, "y": 166, "w": 53, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 9, "w": 53, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0008.png",
"frame": { "x": 104, "y": 166, "w": 53, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 9, "w": 53, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0009.png",
"frame": { "x": 157, "y": 170, "w": 55, "h": 49 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 9, "y": 12, "w": 55, "h": 49 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0010.png",
"frame": { "x": 157, "y": 170, "w": 55, "h": 49 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 9, "y": 12, "w": 55, "h": 49 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0011.png",
"frame": { "x": 0, "y": 115, "w": 53, "h": 54 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 8, "w": 53, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0012.png",
"frame": { "x": 0, "y": 115, "w": 53, "h": 54 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 10, "y": 8, "w": 53, "h": 54 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0013.png",
"frame": { "x": 53, "y": 116, "w": 51, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 11, "y": 6, "w": 51, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0014.png",
"frame": { "x": 53, "y": 116, "w": 51, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 11, "y": 6, "w": 51, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
}, },
{ {
"filename": "0015.png", "filename": "0015.png",
"frame": { "x": 114, "y": 109, "w": 52, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 172,
"y": 110,
"w": 54,
"h": 59
}
}, },
{ {
"filename": "0016.png", "filename": "0016.png",
"frame": { "x": 114, "y": 109, "w": 52, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 9, "y": 5, "w": 52, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 6,
"y": 2,
"w": 54,
"h": 59
},
"frame": {
"x": 172,
"y": 110,
"w": 54,
"h": 59
}
},
{
"filename": "0031.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 4,
"w": 61,
"h": 59
},
"frame": {
"x": 0,
"y": 164,
"w": 61,
"h": 59
}
},
{
"filename": "0032.png",
"rotated": false,
"trimmed": true,
"sourceSize": {
"w": 62,
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 4,
"w": 61,
"h": 59
},
"frame": {
"x": 0,
"y": 164,
"w": 61,
"h": 59
}
}, },
{ {
"filename": "0017.png", "filename": "0017.png",
"frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0018.png", "filename": "0018.png",
"frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0035.png", "filename": "0019.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0036.png", "filename": "0020.png",
"frame": { "x": 0, "y": 58, "w": 55, "h": 57 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 6, "y": 5, "w": 55, "h": 57 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 2,
"y": 0,
"w": 57,
"h": 61
},
"frame": {
"x": 61,
"y": 169,
"w": 57,
"h": 61
}
}, },
{ {
"filename": "0021.png", "filename": "0021.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 2,
"w": 60,
"h": 61
},
"frame": {
"x": 118,
"y": 169,
"w": 60,
"h": 61
}
}, },
{ {
"filename": "0022.png", "filename": "0022.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 0, "filename": "0023.png",
"y": 2, "frame": { "x": 119, "y": 0, "w": 59, "h": 57 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
"spriteSourceSize": { "x": 3, "y": 7, "w": 59, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 118, "filename": "0024.png",
"y": 169, "frame": { "x": 119, "y": 0, "w": 59, "h": 57 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
} "spriteSourceSize": { "x": 3, "y": 7, "w": 59, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0025.png",
"frame": { "x": 178, "y": 0, "w": 60, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 9, "w": 60, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0026.png",
"frame": { "x": 178, "y": 0, "w": 60, "h": 56 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 9, "w": 60, "h": 56 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0027.png",
"frame": { "x": 114, "y": 57, "w": 62, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 2, "y": 12, "w": 62, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0028.png",
"frame": { "x": 114, "y": 57, "w": 62, "h": 52 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 2, "y": 12, "w": 62, "h": 52 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0029.png",
"frame": { "x": 59, "y": 0, "w": 60, "h": 57 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 8, "w": 60, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0030.png",
"frame": { "x": 59, "y": 0, "w": 60, "h": 57 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 8, "w": 60, "h": 57 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0031.png",
"frame": { "x": 0, "y": 0, "w": 59, "h": 58 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 6, "w": 59, "h": 58 },
"sourceSize": { "w": 65, "h": 65 }
},
{
"filename": "0032.png",
"frame": { "x": 0, "y": 0, "w": 59, "h": 58 },
"rotated": false,
"trimmed": true,
"spriteSourceSize": { "x": 3, "y": 6, "w": 59, "h": 58 },
"sourceSize": { "w": 65, "h": 65 }
}, },
{ {
"filename": "0033.png", "filename": "0033.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
},
"spriteSourceSize": {
"x": 0,
"y": 2,
"w": 60,
"h": 61
},
"frame": {
"x": 118,
"y": 169,
"w": 60,
"h": 61
}
}, },
{ {
"filename": "0034.png", "filename": "0034.png",
"frame": { "x": 178, "y": 56, "w": 57, "h": 58 },
"rotated": false, "rotated": false,
"trimmed": true, "trimmed": true,
"sourceSize": { "spriteSourceSize": { "x": 4, "y": 5, "w": 57, "h": 58 },
"w": 62, "sourceSize": { "w": 65, "h": 65 }
"h": 63
}, },
"spriteSourceSize": { {
"x": 0, "filename": "0035.png",
"y": 2, "frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
"spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
"sourceSize": { "w": 65, "h": 65 }
}, },
"frame": { {
"x": 118, "filename": "0036.png",
"y": 169, "frame": { "x": 59, "y": 57, "w": 55, "h": 59 },
"w": 60, "rotated": false,
"h": 61 "trimmed": true,
} "spriteSourceSize": { "x": 6, "y": 3, "w": 55, "h": 59 },
} "sourceSize": { "w": 65, "h": 65 }
]
} }
], ],
"meta": { "meta": {
"app": "https://www.codeandweb.com/texturepacker", "app": "https://www.aseprite.org/",
"version": "3.0", "version": "1.3.8.1-x64",
"smartupdate": "$TexturePacker:SmartUpdate:38ba9918eb8f68ab2190b03c6512ef47:46578d6dd482a1b04fa7c2884107a0f5:fe45e2d628a6cef0908f7b82468c8798$" "image": "47.png",
"format": "I8",
"size": { "w": 238, "h": 223 },
"scale": "1"
} }
} }

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.9 KiB

After

Width:  |  Height:  |  Size: 5.2 KiB

View File

@ -4,7 +4,7 @@ import Pokemon, { EnemyPokemon, PlayerPokemon } from "#app/field/pokemon";
import PokemonSpecies, { allSpecies, getPokemonSpecies, PokemonSpeciesFilter } from "#app/data/pokemon-species"; import PokemonSpecies, { allSpecies, getPokemonSpecies, PokemonSpeciesFilter } from "#app/data/pokemon-species";
import { Constructor, isNullOrUndefined, randSeedInt } from "#app/utils"; import { Constructor, isNullOrUndefined, randSeedInt } from "#app/utils";
import * as Utils from "#app/utils"; import * as Utils from "#app/utils";
import { ConsumableModifier, ConsumablePokemonModifier, DoubleBattleChanceBoosterModifier, ExpBalanceModifier, ExpShareModifier, FusePokemonModifier, HealingBoosterModifier, Modifier, ModifierBar, ModifierPredicate, MultipleParticipantExpBonusModifier, overrideHeldItems, overrideModifiers, PersistentModifier, PokemonExpBoosterModifier, PokemonFormChangeItemModifier, PokemonHeldItemModifier, PokemonHpRestoreModifier, PokemonIncrementingStatModifier, RememberMoveModifier, TerastallizeModifier, TurnHeldItemTransferModifier } from "./modifier/modifier"; import { ConsumableModifier, ConsumablePokemonModifier, DoubleBattleChanceBoosterModifier, ExpBalanceModifier, ExpShareModifier, FusePokemonModifier, HealingBoosterModifier, Modifier, ModifierBar, ModifierPredicate, MultipleParticipantExpBonusModifier, PersistentModifier, PokemonExpBoosterModifier, PokemonFormChangeItemModifier, PokemonHeldItemModifier, PokemonHpRestoreModifier, PokemonIncrementingStatModifier, RememberMoveModifier, TerastallizeModifier, TurnHeldItemTransferModifier } from "./modifier/modifier";
import { PokeballType } from "#enums/pokeball"; import { PokeballType } from "#enums/pokeball";
import { initCommonAnims, initMoveAnim, loadCommonAnimAssets, loadMoveAnimAssets, populateAnims } from "#app/data/battle-anims"; import { initCommonAnims, initMoveAnim, loadCommonAnimAssets, loadMoveAnimAssets, populateAnims } from "#app/data/battle-anims";
import { Phase } from "#app/phase"; import { Phase } from "#app/phase";
@ -47,7 +47,7 @@ import PokemonInfoContainer from "#app/ui/pokemon-info-container";
import { biomeDepths, getBiomeName } from "#app/data/balance/biomes"; import { biomeDepths, getBiomeName } from "#app/data/balance/biomes";
import { SceneBase } from "#app/scene-base"; import { SceneBase } from "#app/scene-base";
import CandyBar from "#app/ui/candy-bar"; import CandyBar from "#app/ui/candy-bar";
import { Variant, variantData } from "#app/data/variant"; import { Variant, variantColorCache, variantData, VariantSet } from "#app/data/variant";
import { Localizable } from "#app/interfaces/locales"; import { Localizable } from "#app/interfaces/locales";
import Overrides from "#app/overrides"; import Overrides from "#app/overrides";
import { InputsController } from "#app/inputs-controller"; import { InputsController } from "#app/inputs-controller";
@ -345,6 +345,33 @@ export default class BattleScene extends SceneBase {
this.load.atlas(key, `images/pokemon/${variant ? "variant/" : ""}${experimental ? "exp/" : ""}${atlasPath}.png`, `images/pokemon/${variant ? "variant/" : ""}${experimental ? "exp/" : ""}${atlasPath}.json`); this.load.atlas(key, `images/pokemon/${variant ? "variant/" : ""}${experimental ? "exp/" : ""}${atlasPath}.png`, `images/pokemon/${variant ? "variant/" : ""}${experimental ? "exp/" : ""}${atlasPath}.json`);
} }
/**
* Load the variant assets for the given sprite and stores them in {@linkcode variantColorCache}
*/
loadPokemonVariantAssets(spriteKey: string, fileRoot: string, variant?: Variant) {
const useExpSprite = this.experimentalSprites && this.hasExpSprite(spriteKey);
if (useExpSprite) {
fileRoot = `exp/${fileRoot}`;
}
let variantConfig = variantData;
fileRoot.split("/").map(p => variantConfig ? variantConfig = variantConfig[p] : null);
const variantSet = variantConfig as VariantSet;
if (variantSet && (variant !== undefined && variantSet[variant] === 1)) {
const populateVariantColors = (key: string): Promise<void> => {
return new Promise(resolve => {
if (variantColorCache.hasOwnProperty(key)) {
return resolve();
}
this.cachedFetch(`./images/pokemon/variant/${fileRoot}.json`).then(res => res.json()).then(c => {
variantColorCache[key] = c;
resolve();
});
});
};
populateVariantColors(spriteKey);
}
}
async preload() { async preload() {
if (DEBUG_RNG) { if (DEBUG_RNG) {
const scene = this; const scene = this;
@ -891,7 +918,7 @@ export default class BattleScene extends SceneBase {
return pokemon; return pokemon;
} }
addEnemyPokemon(species: PokemonSpecies, level: integer, trainerSlot: TrainerSlot, boss: boolean = false, dataSource?: PokemonData, postProcess?: (enemyPokemon: EnemyPokemon) => void): EnemyPokemon { addEnemyPokemon(species: PokemonSpecies, level: integer, trainerSlot: TrainerSlot, boss: boolean = false, shinyLock: boolean = false, dataSource?: PokemonData, postProcess?: (enemyPokemon: EnemyPokemon) => void): EnemyPokemon {
if (Overrides.OPP_LEVEL_OVERRIDE > 0) { if (Overrides.OPP_LEVEL_OVERRIDE > 0) {
level = Overrides.OPP_LEVEL_OVERRIDE; level = Overrides.OPP_LEVEL_OVERRIDE;
} }
@ -901,13 +928,11 @@ export default class BattleScene extends SceneBase {
boss = this.getEncounterBossSegments(this.currentBattle.waveIndex, level, species) > 1; boss = this.getEncounterBossSegments(this.currentBattle.waveIndex, level, species) > 1;
} }
const pokemon = new EnemyPokemon(this, species, level, trainerSlot, boss, dataSource); const pokemon = new EnemyPokemon(this, species, level, trainerSlot, boss, shinyLock, dataSource);
if (Overrides.OPP_FUSION_OVERRIDE) { if (Overrides.OPP_FUSION_OVERRIDE) {
pokemon.generateFusionSpecies(); pokemon.generateFusionSpecies();
} }
overrideModifiers(this, false);
overrideHeldItems(this, pokemon, false);
if (boss && !dataSource) { if (boss && !dataSource) {
const secondaryIvs = Utils.getIvsFromId(Utils.randSeedInt(4294967296)); const secondaryIvs = Utils.getIvsFromId(Utils.randSeedInt(4294967296));
@ -2444,6 +2469,24 @@ export default class BattleScene extends SceneBase {
} }
} }
/**
* Tries to add the input phase to index after target phase in the {@linkcode phaseQueue}, else simply calls {@linkcode unshiftPhase()}
* @param phase {@linkcode Phase} the phase to be added
* @param targetPhase {@linkcode Phase} the type of phase to search for in {@linkcode phaseQueue}
* @returns `true` if a `targetPhase` was found to append to
*/
appendToPhase(phase: Phase, targetPhase: Constructor<Phase>): boolean {
const targetIndex = this.phaseQueue.findIndex(ph => ph instanceof targetPhase);
if (targetIndex !== -1 && this.phaseQueue.length > targetIndex) {
this.phaseQueue.splice(targetIndex + 1, 0, phase);
return true;
} else {
this.unshiftPhase(phase);
return false;
}
}
/** /**
* Adds a MessagePhase, either to PhaseQueuePrepend or nextCommandPhaseQueue * Adds a MessagePhase, either to PhaseQueuePrepend or nextCommandPhaseQueue
* @param message string for MessagePhase * @param message string for MessagePhase
@ -3008,7 +3051,8 @@ export default class BattleScene extends SceneBase {
} }
validateAchv(achv: Achv, args?: unknown[]): boolean { validateAchv(achv: Achv, args?: unknown[]): boolean {
if (!this.gameData.achvUnlocks.hasOwnProperty(achv.id) && achv.validate(this, args)) { if ((!this.gameData.achvUnlocks.hasOwnProperty(achv.id) || Overrides.ACHIEVEMENTS_REUNLOCK_OVERRIDE)
&& achv.validate(this, args)) {
this.gameData.achvUnlocks[achv.id] = new Date().getTime(); this.gameData.achvUnlocks[achv.id] = new Date().getTime();
this.ui.achvBar.showAchv(achv); this.ui.achvBar.showAchv(achv);
if (vouchers.hasOwnProperty(achv.id)) { if (vouchers.hasOwnProperty(achv.id)) {

View File

@ -3735,16 +3735,16 @@ export class PostTurnHurtIfSleepingAbAttr extends PostTurnAbAttr {
/** /**
* Deals damage to all sleeping opponents equal to 1/8 of their max hp (min 1) * Deals damage to all sleeping opponents equal to 1/8 of their max hp (min 1)
* @param {Pokemon} pokemon Pokemon that has this ability * @param pokemon Pokemon that has this ability
* @param {boolean} passive N/A * @param passive N/A
* @param {boolean} simulated true if applying in a simulated call. * @param simulated `true` if applying in a simulated call.
* @param {any[]} args N/A * @param args N/A
* @returns {boolean} true if any opponents are sleeping * @returns `true` if any opponents are sleeping
*/ */
applyPostTurn(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean | Promise<boolean> { applyPostTurn(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean | Promise<boolean> {
let hadEffect: boolean = false; let hadEffect: boolean = false;
for (const opp of pokemon.getOpponents()) { for (const opp of pokemon.getOpponents()) {
if ((opp.status?.effect === StatusEffect.SLEEP || opp.hasAbility(Abilities.COMATOSE)) && !opp.hasAbilityWithAttr(BlockNonDirectDamageAbAttr)) { if ((opp.status?.effect === StatusEffect.SLEEP || opp.hasAbility(Abilities.COMATOSE)) && !opp.hasAbilityWithAttr(BlockNonDirectDamageAbAttr) && !opp.switchOutStatus) {
if (!simulated) { if (!simulated) {
opp.damageAndUpdate(Utils.toDmgValue(opp.getMaxHp() / 8), HitResult.OTHER); opp.damageAndUpdate(Utils.toDmgValue(opp.getMaxHp() / 8), HitResult.OTHER);
pokemon.scene.queueMessage(i18next.t("abilityTriggers:badDreams", { pokemonName: getPokemonNameWithAffix(opp) })); pokemon.scene.queueMessage(i18next.t("abilityTriggers:badDreams", { pokemonName: getPokemonNameWithAffix(opp) }));
@ -4127,9 +4127,13 @@ export class PostBattleAbAttr extends AbAttr {
} }
export class PostBattleLootAbAttr extends PostBattleAbAttr { export class PostBattleLootAbAttr extends PostBattleAbAttr {
/**
* @param args - `[0]`: boolean for if the battle ended in a victory
* @returns `true` if successful
*/
applyPostBattle(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean { applyPostBattle(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean {
const postBattleLoot = pokemon.scene.currentBattle.postBattleLoot; const postBattleLoot = pokemon.scene.currentBattle.postBattleLoot;
if (!simulated && postBattleLoot.length) { if (!simulated && postBattleLoot.length && args[0]) {
const randItem = Utils.randSeedItem(postBattleLoot); const randItem = Utils.randSeedItem(postBattleLoot);
//@ts-ignore - TODO see below //@ts-ignore - TODO see below
if (pokemon.scene.tryTransferHeldItemModifier(randItem, pokemon, true, 1, true, undefined, false)) { // TODO: fix. This is a promise!? if (pokemon.scene.tryTransferHeldItemModifier(randItem, pokemon, true, 1, true, undefined, false)) { // TODO: fix. This is a promise!?
@ -4590,28 +4594,28 @@ export class MoneyAbAttr extends PostBattleAbAttr {
/** /**
* @param pokemon {@linkcode Pokemon} that is the user of this ability. * @param pokemon {@linkcode Pokemon} that is the user of this ability.
* @param passive N/A * @param passive N/A
* @param args N/A * @param args - `[0]`: boolean for if the battle ended in a victory
* @returns true * @returns `true` if successful
*/ */
applyPostBattle(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean { applyPostBattle(pokemon: Pokemon, passive: boolean, simulated: boolean, args: any[]): boolean {
if (!simulated) { if (!simulated && args[0]) {
pokemon.scene.currentBattle.moneyScattered += pokemon.scene.getWaveMoneyAmount(0.2); pokemon.scene.currentBattle.moneyScattered += pokemon.scene.getWaveMoneyAmount(0.2);
}
return true; return true;
} }
return false;
}
} }
/** /**
* Applies a stat change after a Pokémon is summoned, * Applies a stat change after a Pokémon is summoned,
* conditioned on the presence of a specific arena tag. * conditioned on the presence of a specific arena tag.
* *
* @extends {PostSummonStatStageChangeAbAttr} * @extends PostSummonStatStageChangeAbAttr
*/ */
export class PostSummonStatStageChangeOnArenaAbAttr extends PostSummonStatStageChangeAbAttr { export class PostSummonStatStageChangeOnArenaAbAttr extends PostSummonStatStageChangeAbAttr {
/** /**
* The type of arena tag that conditions the stat change. * The type of arena tag that conditions the stat change.
* @private * @private
* @type {ArenaTagType}
*/ */
private tagType: ArenaTagType; private tagType: ArenaTagType;
@ -5079,7 +5083,7 @@ class ForceSwitchOutHelper {
pokemon.scene.clearEnemyHeldItemModifiers(); pokemon.scene.clearEnemyHeldItemModifiers();
if (switchOutTarget.hp) { if (switchOutTarget.hp) {
pokemon.scene.pushPhase(new BattleEndPhase(pokemon.scene)); pokemon.scene.pushPhase(new BattleEndPhase(pokemon.scene, false));
pokemon.scene.pushPhase(new NewBattlePhase(pokemon.scene)); pokemon.scene.pushPhase(new NewBattlePhase(pokemon.scene));
} }
} }
@ -5821,9 +5825,7 @@ export function initAbilities() {
.condition(getSheerForceHitDisableAbCondition()), .condition(getSheerForceHitDisableAbCondition()),
new Ability(Abilities.SHEER_FORCE, 5) new Ability(Abilities.SHEER_FORCE, 5)
.attr(MovePowerBoostAbAttr, (user, target, move) => move.chance >= 1, 5461 / 4096) .attr(MovePowerBoostAbAttr, (user, target, move) => move.chance >= 1, 5461 / 4096)
.attr(MoveEffectChanceMultiplierAbAttr, 0) .attr(MoveEffectChanceMultiplierAbAttr, 0), // Should disable life orb, eject button, red card, kee/maranga berry if they get implemented
.edgeCase() // Should disable shell bell and Meloetta's relic song transformation
.edgeCase(), // Should disable life orb, eject button, red card, kee/maranga berry if they get implemented
new Ability(Abilities.CONTRARY, 5) new Ability(Abilities.CONTRARY, 5)
.attr(StatStageChangeMultiplierAbAttr, -1) .attr(StatStageChangeMultiplierAbAttr, -1)
.ignorable(), .ignorable(),
@ -5891,9 +5893,10 @@ export function initAbilities() {
.attr(WonderSkinAbAttr) .attr(WonderSkinAbAttr)
.ignorable(), .ignorable(),
new Ability(Abilities.ANALYTIC, 5) new Ability(Abilities.ANALYTIC, 5)
.attr(MovePowerBoostAbAttr, (user, target, move) => .attr(MovePowerBoostAbAttr, (user, target, move) => {
!!target?.getLastXMoves(1).find(m => m.turn === target?.scene.currentBattle.turn) const movePhase = user?.scene.findPhase((phase) => phase instanceof MovePhase && phase.pokemon.id !== user.id);
|| user?.scene.currentBattle.turnCommands[target?.getBattlerIndex() ?? BattlerIndex.ATTACKER]?.command !== Command.FIGHT, 1.3), return Utils.isNullOrUndefined(movePhase);
}, 1.3),
new Ability(Abilities.ILLUSION, 5) new Ability(Abilities.ILLUSION, 5)
.attr(UncopiableAbilityAbAttr) .attr(UncopiableAbilityAbAttr)
.attr(UnswappableAbilityAbAttr) .attr(UnswappableAbilityAbAttr)
@ -6049,10 +6052,10 @@ export function initAbilities() {
.attr(PostDefendStatStageChangeAbAttr, (target, user, move) => move.category !== MoveCategory.STATUS, Stat.DEF, 1), .attr(PostDefendStatStageChangeAbAttr, (target, user, move) => move.category !== MoveCategory.STATUS, Stat.DEF, 1),
new Ability(Abilities.WIMP_OUT, 7) new Ability(Abilities.WIMP_OUT, 7)
.attr(PostDamageForceSwitchAbAttr) .attr(PostDamageForceSwitchAbAttr)
.edgeCase(), // Should not trigger when hurting itself in confusion .edgeCase(), // Should not trigger when hurting itself in confusion, causes Fake Out to fail turn 1 and succeed turn 2 if pokemon is switched out before battle start via playing in Switch Mode
new Ability(Abilities.EMERGENCY_EXIT, 7) new Ability(Abilities.EMERGENCY_EXIT, 7)
.attr(PostDamageForceSwitchAbAttr) .attr(PostDamageForceSwitchAbAttr)
.edgeCase(), // Should not trigger when hurting itself in confusion .edgeCase(), // Should not trigger when hurting itself in confusion, causes Fake Out to fail turn 1 and succeed turn 2 if pokemon is switched out before battle start via playing in Switch Mode
new Ability(Abilities.WATER_COMPACTION, 7) new Ability(Abilities.WATER_COMPACTION, 7)
.attr(PostDefendStatStageChangeAbAttr, (target, user, move) => user.getMoveType(move) === Type.WATER && move.category !== MoveCategory.STATUS, Stat.DEF, 2), .attr(PostDefendStatStageChangeAbAttr, (target, user, move) => user.getMoveType(move) === Type.WATER && move.category !== MoveCategory.STATUS, Stat.DEF, 2),
new Ability(Abilities.MERCILESS, 7) new Ability(Abilities.MERCILESS, 7)
@ -6068,7 +6071,7 @@ export function initAbilities() {
.bypassFaint() .bypassFaint()
.partial(), // Meteor form should protect against status effects and yawn .partial(), // Meteor form should protect against status effects and yawn
new Ability(Abilities.STAKEOUT, 7) new Ability(Abilities.STAKEOUT, 7)
.attr(MovePowerBoostAbAttr, (user, target, move) => user?.scene.currentBattle.turnCommands[target?.getBattlerIndex() ?? BattlerIndex.ATTACKER]?.command === Command.POKEMON, 2), .attr(MovePowerBoostAbAttr, (user, target, move) => !!target?.turnData.switchedInThisTurn, 2),
new Ability(Abilities.WATER_BUBBLE, 7) new Ability(Abilities.WATER_BUBBLE, 7)
.attr(ReceivedTypeDamageMultiplierAbAttr, Type.FIRE, 0.5) .attr(ReceivedTypeDamageMultiplierAbAttr, Type.FIRE, 0.5)
.attr(MoveTypePowerBoostAbAttr, Type.WATER, 2) .attr(MoveTypePowerBoostAbAttr, Type.WATER, 2)
@ -6461,8 +6464,7 @@ export function initAbilities() {
.attr(IgnoreOpponentStatStagesAbAttr, [ Stat.EVA ]) .attr(IgnoreOpponentStatStagesAbAttr, [ Stat.EVA ])
.ignorable(), .ignorable(),
new Ability(Abilities.SUPERSWEET_SYRUP, 9) new Ability(Abilities.SUPERSWEET_SYRUP, 9)
.attr(PostSummonStatStageChangeAbAttr, [ Stat.EVA ], -1) .attr(PostSummonStatStageChangeAbAttr, [ Stat.EVA ], -1),
.condition(getOncePerBattleCondition(Abilities.SUPERSWEET_SYRUP)),
new Ability(Abilities.HOSPITALITY, 9) new Ability(Abilities.HOSPITALITY, 9)
.attr(PostSummonAllyHealAbAttr, 4, true), .attr(PostSummonAllyHealAbAttr, 4, true),
new Ability(Abilities.TOXIC_CHAIN, 9) new Ability(Abilities.TOXIC_CHAIN, 9)

View File

@ -1144,7 +1144,7 @@ class FireGrassPledgeTag extends ArenaTag {
? arena.scene.getPlayerField() ? arena.scene.getPlayerField()
: arena.scene.getEnemyField(); : arena.scene.getEnemyField();
field.filter(pokemon => !pokemon.isOfType(Type.FIRE)).forEach(pokemon => { field.filter(pokemon => !pokemon.isOfType(Type.FIRE) && !pokemon.switchOutStatus).forEach(pokemon => {
// "{pokemonNameWithAffix} was hurt by the sea of fire!" // "{pokemonNameWithAffix} was hurt by the sea of fire!"
pokemon.scene.queueMessage(i18next.t("arenaTag:fireGrassPledgeLapse", { pokemonNameWithAffix: getPokemonNameWithAffix(pokemon) })); pokemon.scene.queueMessage(i18next.t("arenaTag:fireGrassPledgeLapse", { pokemonNameWithAffix: getPokemonNameWithAffix(pokemon) }));
// TODO: Replace this with a proper animation // TODO: Replace this with a proper animation

View File

@ -7,16 +7,16 @@ import { Species } from "#enums/species";
export const speciesEggMoves = { export const speciesEggMoves = {
[Species.BULBASAUR]: [ Moves.SAPPY_SEED, Moves.MALIGNANT_CHAIN, Moves.EARTH_POWER, Moves.MATCHA_GOTCHA ], [Species.BULBASAUR]: [ Moves.SAPPY_SEED, Moves.MALIGNANT_CHAIN, Moves.EARTH_POWER, Moves.MATCHA_GOTCHA ],
[Species.CHARMANDER]: [ Moves.DRAGON_DANCE, Moves.BITTER_BLADE, Moves.EARTH_POWER, Moves.OBLIVION_WING ], [Species.CHARMANDER]: [ Moves.DRAGON_DANCE, Moves.BITTER_BLADE, Moves.EARTH_POWER, Moves.OBLIVION_WING ],
[Species.SQUIRTLE]: [ Moves.FREEZE_DRY, Moves.SHORE_UP, Moves.BOUNCY_BUBBLE, Moves.ORIGIN_PULSE ], [Species.SQUIRTLE]: [ Moves.FREEZE_DRY, Moves.ARMOR_CANNON, Moves.BOUNCY_BUBBLE, Moves.ORIGIN_PULSE ],
[Species.CATERPIE]: [ Moves.SANDSEAR_STORM, Moves.SILK_TRAP, Moves.TWIN_BEAM, Moves.BLEAKWIND_STORM ], [Species.CATERPIE]: [ Moves.SANDSEAR_STORM, Moves.SILK_TRAP, Moves.TWIN_BEAM, Moves.BLEAKWIND_STORM ],
[Species.WEEDLE]: [ Moves.THOUSAND_ARROWS, Moves.NOXIOUS_TORQUE, Moves.ATTACK_ORDER, Moves.VICTORY_DANCE ], [Species.WEEDLE]: [ Moves.THOUSAND_ARROWS, Moves.NOXIOUS_TORQUE, Moves.ATTACK_ORDER, Moves.VICTORY_DANCE ],
[Species.PIDGEY]: [ Moves.WILDBOLT_STORM, Moves.SANDSEAR_STORM, Moves.NASTY_PLOT, Moves.BOOMBURST ], [Species.PIDGEY]: [ Moves.WILDBOLT_STORM, Moves.SANDSEAR_STORM, Moves.NASTY_PLOT, Moves.BOOMBURST ],
[Species.RATTATA]: [ Moves.HYPER_FANG, Moves.PSYCHIC_FANGS, Moves.FIRE_FANG, Moves.EXTREME_SPEED ], [Species.RATTATA]: [ Moves.HYPER_FANG, Moves.PSYCHIC_FANGS, Moves.FIRE_FANG, Moves.EXTREME_SPEED ],
[Species.SPEAROW]: [ Moves.FLOATY_FALL, Moves.EXTREME_SPEED, Moves.TIDY_UP, Moves.TRIPLE_ARROWS ], [Species.SPEAROW]: [ Moves.FLOATY_FALL, Moves.HYPER_DRILL, Moves.TIDY_UP, Moves.TRIPLE_ARROWS ],
[Species.EKANS]: [ Moves.NOXIOUS_TORQUE, Moves.DRAGON_DANCE, Moves.SLACK_OFF, Moves.SHED_TAIL ], [Species.EKANS]: [ Moves.NOXIOUS_TORQUE, Moves.DRAGON_DANCE, Moves.SLACK_OFF, Moves.SHED_TAIL ],
[Species.SANDSHREW]: [ Moves.HIGH_HORSEPOWER, Moves.DIRE_CLAW, Moves.SHORE_UP, Moves.MIGHTY_CLEAVE ], [Species.SANDSHREW]: [ Moves.HIGH_HORSEPOWER, Moves.DIRE_CLAW, Moves.SHORE_UP, Moves.MIGHTY_CLEAVE ],
[Species.NIDORAN_F]: [ Moves.NO_RETREAT, Moves.BANEFUL_BUNKER, Moves.SANDSEAR_STORM, Moves.MALIGNANT_CHAIN ], [Species.NIDORAN_F]: [ Moves.CALM_MIND, Moves.MOONLIGHT, Moves.MALIGNANT_CHAIN, Moves.SANDSEAR_STORM ],
[Species.NIDORAN_M]: [ Moves.NOXIOUS_TORQUE, Moves.KINGS_SHIELD, Moves.NO_RETREAT, Moves.PRECIPICE_BLADES ], [Species.NIDORAN_M]: [ Moves.DRAGON_DANCE, Moves.MOUNTAIN_GALE, Moves.NOXIOUS_TORQUE, Moves.PRECIPICE_BLADES ],
[Species.VULPIX]: [ Moves.MOONBLAST, Moves.INFERNAL_PARADE, Moves.MORNING_SUN, Moves.TAIL_GLOW ], [Species.VULPIX]: [ Moves.MOONBLAST, Moves.INFERNAL_PARADE, Moves.MORNING_SUN, Moves.TAIL_GLOW ],
[Species.ZUBAT]: [ Moves.FLOATY_FALL, Moves.DIRE_CLAW, Moves.SWORDS_DANCE, Moves.COLLISION_COURSE ], [Species.ZUBAT]: [ Moves.FLOATY_FALL, Moves.DIRE_CLAW, Moves.SWORDS_DANCE, Moves.COLLISION_COURSE ],
[Species.ODDISH]: [ Moves.SLUDGE_BOMB, Moves.FIERY_DANCE, Moves.STRENGTH_SAP, Moves.SPORE ], [Species.ODDISH]: [ Moves.SLUDGE_BOMB, Moves.FIERY_DANCE, Moves.STRENGTH_SAP, Moves.SPORE ],
@ -31,105 +31,107 @@ export const speciesEggMoves = {
[Species.ABRA]: [ Moves.AURA_SPHERE, Moves.BADDY_BAD, Moves.ICE_BEAM, Moves.PSYSTRIKE ], [Species.ABRA]: [ Moves.AURA_SPHERE, Moves.BADDY_BAD, Moves.ICE_BEAM, Moves.PSYSTRIKE ],
[Species.MACHOP]: [ Moves.COMBAT_TORQUE, Moves.METEOR_MASH, Moves.MOUNTAIN_GALE, Moves.FISSURE ], [Species.MACHOP]: [ Moves.COMBAT_TORQUE, Moves.METEOR_MASH, Moves.MOUNTAIN_GALE, Moves.FISSURE ],
[Species.BELLSPROUT]: [ Moves.SOLAR_BLADE, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.VICTORY_DANCE ], [Species.BELLSPROUT]: [ Moves.SOLAR_BLADE, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.VICTORY_DANCE ],
[Species.TENTACOOL]: [ Moves.BANEFUL_BUNKER, Moves.STRENGTH_SAP, Moves.BOUNCY_BUBBLE, Moves.MALIGNANT_CHAIN ], [Species.TENTACOOL]: [ Moves.BANEFUL_BUNKER, Moves.MALIGNANT_CHAIN, Moves.BOUNCY_BUBBLE, Moves.STRENGTH_SAP ],
[Species.GEODUDE]: [ Moves.FLARE_BLITZ, Moves.HEAD_SMASH, Moves.SHORE_UP, Moves.SHELL_SMASH ], [Species.GEODUDE]: [ Moves.FLARE_BLITZ, Moves.HEAD_SMASH, Moves.SHORE_UP, Moves.SHELL_SMASH ],
[Species.PONYTA]: [ Moves.HIGH_HORSEPOWER, Moves.FIRE_LASH, Moves.SWORDS_DANCE, Moves.VOLT_TACKLE ], [Species.PONYTA]: [ Moves.HEADLONG_RUSH, Moves.FIRE_LASH, Moves.SWORDS_DANCE, Moves.VOLT_TACKLE ],
[Species.SLOWPOKE]: [ Moves.BOUNCY_BUBBLE, Moves.FLAMETHROWER, Moves.MYSTICAL_POWER, Moves.SHED_TAIL ], [Species.SLOWPOKE]: [ Moves.BOUNCY_BUBBLE, Moves.FROST_BREATH, Moves.SHED_TAIL, Moves.MYSTICAL_POWER ],
[Species.MAGNEMITE]: [ Moves.PARABOLIC_CHARGE, Moves.FLAMETHROWER, Moves.ICE_BEAM, Moves.THUNDERCLAP ], [Species.MAGNEMITE]: [ Moves.PARABOLIC_CHARGE, Moves.FLAMETHROWER, Moves.ICE_BEAM, Moves.THUNDERCLAP ],
[Species.FARFETCHD]: [ Moves.IVY_CUDGEL, Moves.TRIPLE_ARROWS, Moves.DRILL_RUN, Moves.VICTORY_DANCE ], [Species.FARFETCHD]: [ Moves.IVY_CUDGEL, Moves.TRIPLE_ARROWS, Moves.DRILL_RUN, Moves.VICTORY_DANCE ],
[Species.DODUO]: [ Moves.TRIPLE_AXEL, Moves.MULTI_ATTACK, Moves.FLOATY_FALL, Moves.TRIPLE_ARROWS ], [Species.DODUO]: [ Moves.TRIPLE_AXEL, Moves.HYPER_DRILL, Moves.FLOATY_FALL, Moves.TRIPLE_ARROWS ],
[Species.SEEL]: [ Moves.FREEZE_DRY, Moves.BOUNCY_BUBBLE, Moves.SLACK_OFF, Moves.STEAM_ERUPTION ], [Species.SEEL]: [ Moves.FREEZE_DRY, Moves.BOUNCY_BUBBLE, Moves.SLACK_OFF, Moves.STEAM_ERUPTION ],
[Species.GRIMER]: [ Moves.SUCKER_PUNCH, Moves.CURSE, Moves.STRENGTH_SAP, Moves.NOXIOUS_TORQUE ], [Species.GRIMER]: [ Moves.SUCKER_PUNCH, Moves.CURSE, Moves.NOXIOUS_TORQUE, Moves.STRENGTH_SAP ],
[Species.SHELLDER]: [ Moves.ROCK_BLAST, Moves.WATER_SHURIKEN, Moves.BANEFUL_BUNKER, Moves.BONE_RUSH ], [Species.SHELLDER]: [ Moves.ROCK_BLAST, Moves.WATER_SHURIKEN, Moves.BANEFUL_BUNKER, Moves.BONE_RUSH ],
[Species.GASTLY]: [ Moves.SLUDGE_BOMB, Moves.AURA_SPHERE, Moves.NASTY_PLOT, Moves.ASTRAL_BARRAGE ], [Species.GASTLY]: [ Moves.MALIGNANT_CHAIN, Moves.AURA_SPHERE, Moves.PARTING_SHOT, Moves.DARK_VOID ],
[Species.ONIX]: [ Moves.SHORE_UP, Moves.THOUSAND_WAVES, Moves.COIL, Moves.DIAMOND_STORM ], [Species.ONIX]: [ Moves.SHORE_UP, Moves.THOUSAND_WAVES, Moves.COIL, Moves.DIAMOND_STORM ],
[Species.DROWZEE]: [ Moves.BADDY_BAD, Moves.STRENGTH_SAP, Moves.LUMINA_CRASH, Moves.DARK_VOID ], [Species.DROWZEE]: [ Moves.BADDY_BAD, Moves.STRENGTH_SAP, Moves.LUMINA_CRASH, Moves.DARK_VOID ],
[Species.KRABBY]: [ Moves.DIRE_CLAW, Moves.JET_PUNCH, Moves.IVY_CUDGEL, Moves.SHELL_SMASH ], [Species.KRABBY]: [ Moves.DIRE_CLAW, Moves.DRAGON_HAMMER, Moves.IVY_CUDGEL, Moves.JET_PUNCH ],
[Species.VOLTORB]: [ Moves.NASTY_PLOT, Moves.FUSION_FLARE, Moves.FROST_BREATH, Moves.ELECTRO_DRIFT ], [Species.VOLTORB]: [ Moves.NASTY_PLOT, Moves.FUSION_FLARE, Moves.FROST_BREATH, Moves.ELECTRO_DRIFT ],
[Species.EXEGGCUTE]: [ Moves.FICKLE_BEAM, Moves.APPLE_ACID, Moves.TRICK_ROOM, Moves.LUMINA_CRASH ], [Species.EXEGGCUTE]: [ Moves.FICKLE_BEAM, Moves.APPLE_ACID, Moves.TRICK_ROOM, Moves.LUMINA_CRASH ],
[Species.CUBONE]: [ Moves.HEAD_SMASH, Moves.WOOD_HAMMER, Moves.SHADOW_SNEAK, Moves.BITTER_BLADE ], [Species.CUBONE]: [ Moves.HEAD_SMASH, Moves.WOOD_HAMMER, Moves.SHADOW_SNEAK, Moves.BITTER_BLADE ],
[Species.LICKITUNG]: [ Moves.CRUSH_GRIP, Moves.FIRE_LASH, Moves.SLACK_OFF, Moves.MAGICAL_TORQUE ], [Species.LICKITUNG]: [ Moves.CRUSH_GRIP, Moves.FIRE_LASH, Moves.SLACK_OFF, Moves.MAGICAL_TORQUE ],
[Species.KOFFING]: [ Moves.SCALD, Moves.RECOVER, Moves.BODY_PRESS, Moves.MALIGNANT_CHAIN ], [Species.KOFFING]: [ Moves.SCALD, Moves.RECOVER, Moves.BODY_PRESS, Moves.MALIGNANT_CHAIN ],
[Species.RHYHORN]: [ Moves.SHORE_UP, Moves.ICE_HAMMER, Moves.ACCELEROCK, Moves.HEAD_SMASH ], [Species.RHYHORN]: [ Moves.SHORE_UP, Moves.ICE_HAMMER, Moves.ACCELEROCK, Moves.HEAD_SMASH ],
[Species.TANGELA]: [ Moves.STRENGTH_SAP, Moves.SNAP_TRAP, Moves.PARTING_SHOT, Moves.SAPPY_SEED ], [Species.TANGELA]: [ Moves.NATURES_MADNESS, Moves.SNAP_TRAP, Moves.PARTING_SHOT, Moves.SAPPY_SEED ],
[Species.KANGASKHAN]: [ Moves.POWER_UP_PUNCH, Moves.TRAILBLAZE, Moves.FACADE, Moves.SEISMIC_TOSS ], [Species.KANGASKHAN]: [ Moves.POWER_UP_PUNCH, Moves.TRAILBLAZE, Moves.FACADE, Moves.SEISMIC_TOSS ],
[Species.HORSEA]: [ Moves.SNIPE_SHOT, Moves.FROST_BREATH, Moves.HURRICANE, Moves.SPACIAL_REND ], [Species.HORSEA]: [ Moves.SNIPE_SHOT, Moves.FROST_BREATH, Moves.SLUDGE_BOMB, Moves.CLANGING_SCALES ],
[Species.GOLDEEN]: [ Moves.GLACIAL_LANCE, Moves.SUPERCELL_SLAM, Moves.DRAGON_DANCE, Moves.FISHIOUS_REND ], [Species.GOLDEEN]: [ Moves.GLACIAL_LANCE, Moves.SUPERCELL_SLAM, Moves.DRAGON_DANCE, Moves.FISHIOUS_REND ],
[Species.STARYU]: [ Moves.CALM_MIND, Moves.BOUNCY_BUBBLE, Moves.MOONBLAST, Moves.MYSTICAL_POWER ], [Species.STARYU]: [ Moves.CALM_MIND, Moves.BOUNCY_BUBBLE, Moves.MOONBLAST, Moves.MYSTICAL_POWER ],
[Species.SCYTHER]: [ Moves.MIGHTY_CLEAVE, Moves.BUG_BITE, Moves.STORM_THROW, Moves.DOUBLE_IRON_BASH ], [Species.SCYTHER]: [ Moves.MIGHTY_CLEAVE, Moves.GEAR_GRIND, Moves.STORM_THROW, Moves.BITTER_BLADE ],
[Species.PINSIR]: [ Moves.HEADLONG_RUSH, Moves.LEECH_LIFE, Moves.CRUSH_GRIP, Moves.EXTREME_SPEED ], [Species.PINSIR]: [ Moves.HEADLONG_RUSH, Moves.LEECH_LIFE, Moves.CRUSH_GRIP, Moves.EXTREME_SPEED ],
[Species.TAUROS]: [ Moves.HIGH_HORSEPOWER, Moves.FIRE_LASH, Moves.LIQUIDATION, Moves.COMBAT_TORQUE ], [Species.TAUROS]: [ Moves.SWORDS_DANCE, Moves.FIRE_LASH, Moves.WICKED_TORQUE, Moves.COLLISION_COURSE ],
[Species.MAGIKARP]: [ Moves.FLIP_TURN, Moves.ICE_SPINNER, Moves.DRAGON_ASCENT, Moves.SURGING_STRIKES ], [Species.MAGIKARP]: [ Moves.FLIP_TURN, Moves.ICE_SPINNER, Moves.DRAGON_ASCENT, Moves.SURGING_STRIKES ],
[Species.LAPRAS]: [ Moves.RECOVER, Moves.FREEZE_DRY, Moves.SCALD, Moves.SHELL_SMASH ], [Species.LAPRAS]: [ Moves.RECOVER, Moves.FREEZE_DRY, Moves.SCALD, Moves.SHELL_SMASH ],
[Species.DITTO]: [ Moves.MIMIC, Moves.SKETCH, Moves.METRONOME, Moves.IMPRISON ], [Species.DITTO]: [ Moves.MIMIC, Moves.SKETCH, Moves.METRONOME, Moves.IMPRISON ],
[Species.EEVEE]: [ Moves.WISH, Moves.NO_RETREAT, Moves.ZIPPY_ZAP, Moves.BOOMBURST ], [Species.EEVEE]: [ Moves.WISH, Moves.NO_RETREAT, Moves.ZIPPY_ZAP, Moves.BOOMBURST ],
[Species.PORYGON]: [ Moves.THUNDERCLAP, Moves.AURA_SPHERE, Moves.FLAMETHROWER, Moves.TECHNO_BLAST ], [Species.PORYGON]: [ Moves.THUNDERCLAP, Moves.AURA_SPHERE, Moves.FLAMETHROWER, Moves.TECHNO_BLAST ],
[Species.OMANYTE]: [ Moves.FREEZE_DRY, Moves.EARTH_POWER, Moves.POWER_GEM, Moves.STEAM_ERUPTION ], [Species.OMANYTE]: [ Moves.FREEZE_DRY, Moves.GIGA_DRAIN, Moves.POWER_GEM, Moves.STEAM_ERUPTION ],
[Species.KABUTO]: [ Moves.CEASELESS_EDGE, Moves.HIGH_HORSEPOWER, Moves.TRIPLE_DIVE, Moves.MIGHTY_CLEAVE ], [Species.KABUTO]: [ Moves.CEASELESS_EDGE, Moves.HIGH_HORSEPOWER, Moves.CRABHAMMER, Moves.MIGHTY_CLEAVE ],
[Species.AERODACTYL]: [ Moves.FLOATY_FALL, Moves.FLARE_BLITZ, Moves.SWORDS_DANCE, Moves.MIGHTY_CLEAVE ], [Species.AERODACTYL]: [ Moves.FLOATY_FALL, Moves.FLARE_BLITZ, Moves.SWORDS_DANCE, Moves.MIGHTY_CLEAVE ],
[Species.ARTICUNO]: [ Moves.EARTH_POWER, Moves.CALM_MIND, Moves.AURORA_VEIL, Moves.AEROBLAST ], [Species.ARTICUNO]: [ Moves.EARTH_POWER, Moves.CALM_MIND, Moves.AURORA_VEIL, Moves.AEROBLAST ],
[Species.ZAPDOS]: [ Moves.BLEAKWIND_STORM, Moves.CALM_MIND, Moves.SANDSEAR_STORM, Moves.ELECTRO_SHOT ], [Species.ZAPDOS]: [ Moves.BLEAKWIND_STORM, Moves.CALM_MIND, Moves.SANDSEAR_STORM, Moves.ELECTRO_SHOT ],
[Species.MOLTRES]: [ Moves.SCORCHING_SANDS, Moves.CALM_MIND, Moves.AEROBLAST, Moves.TORCH_SONG ], [Species.MOLTRES]: [ Moves.EARTH_POWER, Moves.CALM_MIND, Moves.AEROBLAST, Moves.TORCH_SONG ],
[Species.DRATINI]: [ Moves.DRAGON_HAMMER, Moves.CRUSH_GRIP, Moves.FIRE_LASH, Moves.GIGATON_HAMMER ], [Species.DRATINI]: [ Moves.DRAGON_HAMMER, Moves.CRUSH_GRIP, Moves.FIRE_LASH, Moves.GIGATON_HAMMER ],
[Species.MEWTWO]: [ Moves.METEOR_MASH, Moves.MOONBLAST, Moves.THUNDEROUS_KICK, Moves.PHOTON_GEYSER ], [Species.MEWTWO]: [ Moves.METEOR_MASH, Moves.MOONBLAST, Moves.THUNDEROUS_KICK, Moves.PHOTON_GEYSER ],
[Species.MEW]: [ Moves.PHOTON_GEYSER, Moves.MOONBLAST, Moves.ASTRAL_BARRAGE, Moves.SHELL_SMASH ], [Species.MEW]: [ Moves.PHOTON_GEYSER, Moves.MOONBLAST, Moves.ASTRAL_BARRAGE, Moves.SHELL_SMASH ],
[Species.CHIKORITA]: [ Moves.SAPPY_SEED, Moves.STONE_AXE, Moves.DRAGON_DANCE, Moves.SPORE ], [Species.CHIKORITA]: [ Moves.SAPPY_SEED, Moves.STONE_AXE, Moves.DRAGON_DANCE, Moves.SPORE ],
[Species.CYNDAQUIL]: [ Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.FIERY_DANCE, Moves.ELECTRO_DRIFT ], [Species.CYNDAQUIL]: [ Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.FIERY_DANCE, Moves.ELECTRO_DRIFT ],
[Species.TOTODILE]: [ Moves.THUNDER_PUNCH, Moves.DRAGON_DANCE, Moves.TRIPLE_AXEL, Moves.FISHIOUS_REND ], [Species.TOTODILE]: [ Moves.THUNDER_PUNCH, Moves.DRAGON_DANCE, Moves.TRIPLE_AXEL, Moves.SURGING_STRIKES ],
[Species.SENTRET]: [ Moves.TIDY_UP, Moves.FAKE_OUT, Moves.NUZZLE, Moves.EXTREME_SPEED ], [Species.SENTRET]: [ Moves.TIDY_UP, Moves.FAKE_OUT, Moves.NUZZLE, Moves.EXTREME_SPEED ],
[Species.HOOTHOOT]: [ Moves.CALM_MIND, Moves.ESPER_WING, Moves.AEROBLAST, Moves.BOOMBURST ], [Species.HOOTHOOT]: [ Moves.CALM_MIND, Moves.ESPER_WING, Moves.AEROBLAST, Moves.BOOMBURST ],
[Species.LEDYBA]: [ Moves.POLLEN_PUFF, Moves.THIEF, Moves.PARTING_SHOT, Moves.SPORE ], [Species.LEDYBA]: [ Moves.POLLEN_PUFF, Moves.MAT_BLOCK, Moves.PARTING_SHOT, Moves.SPORE ],
[Species.SPINARAK]: [ Moves.PARTING_SHOT, Moves.ATTACK_ORDER, Moves.GASTRO_ACID, Moves.STRENGTH_SAP ], [Species.SPINARAK]: [ Moves.PARTING_SHOT, Moves.ATTACK_ORDER, Moves.GASTRO_ACID, Moves.STRENGTH_SAP ],
[Species.CHINCHOU]: [ Moves.THUNDERCLAP, Moves.BOUNCY_BUBBLE, Moves.THUNDER_CAGE, Moves.TAIL_GLOW ], [Species.CHINCHOU]: [ Moves.THUNDERCLAP, Moves.BOUNCY_BUBBLE, Moves.THUNDER_CAGE, Moves.TAIL_GLOW ],
[Species.PICHU]: [ Moves.MOONBLAST, Moves.TRIPLE_AXEL, Moves.FIERY_DANCE, Moves.AURA_WHEEL ], [Species.PICHU]: [ Moves.MOONBLAST, Moves.TRIPLE_AXEL, Moves.FIERY_DANCE, Moves.AURA_WHEEL ],
[Species.CLEFFA]: [ Moves.CALM_MIND, Moves.EARTH_POWER, Moves.WISH, Moves.LIGHT_OF_RUIN ], [Species.CLEFFA]: [ Moves.CALM_MIND, Moves.EARTH_POWER, Moves.WISH, Moves.LIGHT_OF_RUIN ],
[Species.IGGLYBUFF]: [ Moves.DRAIN_PUNCH, Moves.GRAV_APPLE, Moves.SOFT_BOILED, Moves.EXTREME_SPEED ], [Species.IGGLYBUFF]: [ Moves.DRAIN_PUNCH, Moves.GRAV_APPLE, Moves.SOFT_BOILED, Moves.EXTREME_SPEED ],
[Species.TOGEPI]: [ Moves.SCORCHING_SANDS, Moves.ROOST, Moves.RELIC_SONG, Moves.FIERY_DANCE ], [Species.TOGEPI]: [ Moves.SCORCHING_SANDS, Moves.SPLISHY_SPLASH, Moves.RELIC_SONG, Moves.FIERY_DANCE ],
[Species.NATU]: [ Moves.AEROBLAST, Moves.ROOST, Moves.MOONBLAST, Moves.LUMINA_CRASH ], [Species.NATU]: [ Moves.REVIVAL_BLESSING, Moves.NASTY_PLOT, Moves.MOONBLAST, Moves.OBLIVION_WING ],
[Species.MAREEP]: [ Moves.ICE_BEAM, Moves.PARABOLIC_CHARGE, Moves.CORE_ENFORCER, Moves.TAIL_GLOW ], [Species.MAREEP]: [ Moves.ICE_BEAM, Moves.PARABOLIC_CHARGE, Moves.CORE_ENFORCER, Moves.TAIL_GLOW ],
[Species.HOPPIP]: [ Moves.FLOATY_FALL, Moves.STRENGTH_SAP, Moves.SAPPY_SEED, Moves.SPORE ], [Species.HOPPIP]: [ Moves.FLOATY_FALL, Moves.STRENGTH_SAP, Moves.SAPPY_SEED, Moves.SPORE ],
[Species.AIPOM]: [ Moves.TIDY_UP, Moves.STORM_THROW, Moves.FAKE_OUT, Moves.POPULATION_BOMB ], [Species.AIPOM]: [ Moves.ROCK_BLAST, Moves.STORM_THROW, Moves.FAKE_OUT, Moves.SWORDS_DANCE ],
[Species.SUNKERN]: [ Moves.SPORE, Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.HYDRO_STEAM ], [Species.SUNKERN]: [ Moves.SPORE, Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.HYDRO_STEAM ],
[Species.YANMA]: [ Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.HEAT_WAVE, Moves.BLEAKWIND_STORM ], [Species.YANMA]: [ Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.HEAT_WAVE, Moves.BLEAKWIND_STORM ],
[Species.WOOPER]: [ Moves.SIZZLY_SLIDE, Moves.RECOVER, Moves.CURSE, Moves.SURGING_STRIKES ], [Species.WOOPER]: [ Moves.SIZZLY_SLIDE, Moves.RECOVER, Moves.SHED_TAIL, Moves.SURGING_STRIKES ],
[Species.MURKROW]: [ Moves.TRIPLE_ARROWS, Moves.FLOATY_FALL, Moves.TIDY_UP, Moves.WICKED_BLOW ], [Species.MURKROW]: [ Moves.TRIPLE_ARROWS, Moves.FLOATY_FALL, Moves.TIDY_UP, Moves.WICKED_BLOW ],
[Species.MISDREAVUS]: [ Moves.TAKE_HEART, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.ASTRAL_BARRAGE ], [Species.MISDREAVUS]: [ Moves.TAKE_HEART, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.MOONGEIST_BEAM ],
[Species.UNOWN]: [ Moves.NATURE_POWER, Moves.COSMIC_POWER, Moves.ANCIENT_POWER, Moves.MYSTICAL_POWER ], [Species.UNOWN]: [ Moves.NATURE_POWER, Moves.COSMIC_POWER, Moves.ANCIENT_POWER, Moves.MYSTICAL_POWER ],
[Species.GIRAFARIG]: [ Moves.MYSTICAL_POWER, Moves.NIGHT_DAZE, Moves.RECOVER, Moves.BOOMBURST ], [Species.GIRAFARIG]: [ Moves.MYSTICAL_POWER, Moves.NIGHT_DAZE, Moves.RECOVER, Moves.BOOMBURST ],
[Species.PINECO]: [ Moves.METAL_BURST, Moves.SHORE_UP, Moves.BODY_PRESS, Moves.DIAMOND_STORM ], [Species.PINECO]: [ Moves.METAL_BURST, Moves.SHORE_UP, Moves.BODY_PRESS, Moves.DIAMOND_STORM ],
[Species.DUNSPARCE]: [ Moves.WICKED_TORQUE, Moves.MAGICAL_TORQUE, Moves.BLAZING_TORQUE, Moves.EXTREME_SPEED ], [Species.DUNSPARCE]: [ Moves.WICKED_TORQUE, Moves.MAGICAL_TORQUE, Moves.BLAZING_TORQUE, Moves.EXTREME_SPEED ],
[Species.GLIGAR]: [ Moves.FLOATY_FALL, Moves.THOUSAND_WAVES, Moves.ROOST, Moves.MIGHTY_CLEAVE ], [Species.GLIGAR]: [ Moves.FLOATY_FALL, Moves.THOUSAND_WAVES, Moves.SPIKY_SHIELD, Moves.MIGHTY_CLEAVE ],
[Species.SNUBBULL]: [ Moves.FACADE, Moves.EARTHQUAKE, Moves.SWORDS_DANCE, Moves.EXTREME_SPEED ], [Species.SNUBBULL]: [ Moves.FACADE, Moves.HIGH_HORSEPOWER, Moves.SWORDS_DANCE, Moves.EXTREME_SPEED ],
[Species.QWILFISH]: [ Moves.BARB_BARRAGE, Moves.BANEFUL_BUNKER, Moves.KNOCK_OFF, Moves.FISHIOUS_REND ], [Species.QWILFISH]: [ Moves.BARB_BARRAGE, Moves.BANEFUL_BUNKER, Moves.RECOVER, Moves.FISHIOUS_REND ],
[Species.SHUCKLE]: [ Moves.STUFF_CHEEKS, Moves.HEAL_ORDER, Moves.BODY_PRESS, Moves.SALT_CURE ], [Species.SHUCKLE]: [ Moves.STUFF_CHEEKS, Moves.HEAL_ORDER, Moves.BODY_PRESS, Moves.SALT_CURE ],
[Species.HERACROSS]: [ Moves.ROCK_BLAST, Moves.FIRST_IMPRESSION, Moves.ICICLE_SPEAR, Moves.DRAGON_DANCE ], [Species.HERACROSS]: [ Moves.ROCK_BLAST, Moves.FIRST_IMPRESSION, Moves.ICICLE_SPEAR, Moves.TIDY_UP ],
[Species.SNEASEL]: [ Moves.DIRE_CLAW, Moves.STORM_THROW, Moves.TRIPLE_AXEL, Moves.WICKED_BLOW ], [Species.SNEASEL]: [ Moves.DIRE_CLAW, Moves.DARKEST_LARIAT, Moves.TRIPLE_AXEL, Moves.CLOSE_COMBAT ],
[Species.TEDDIURSA]: [ Moves.MOUNTAIN_GALE, Moves.FAKE_OUT, Moves.SLACK_OFF, Moves.PRECIPICE_BLADES ], [Species.TEDDIURSA]: [ Moves.MOUNTAIN_GALE, Moves.FAKE_OUT, Moves.SLACK_OFF, Moves.PRECIPICE_BLADES ],
[Species.SLUGMA]: [ Moves.BURNING_BULWARK, Moves.POWER_GEM, Moves.SOLAR_BEAM, Moves.MAGMA_STORM ], [Species.SLUGMA]: [ Moves.BURNING_BULWARK, Moves.POWER_GEM, Moves.SOLAR_BEAM, Moves.MAGMA_STORM ],
[Species.SWINUB]: [ Moves.SLACK_OFF, Moves.LANDS_WRATH, Moves.MIGHTY_CLEAVE, Moves.GLACIAL_LANCE ], [Species.SWINUB]: [ Moves.SLACK_OFF, Moves.MOUNTAIN_GALE, Moves.STONE_AXE, Moves.PRECIPICE_BLADES ],
[Species.CORSOLA]: [ Moves.SCALD, Moves.FREEZE_DRY, Moves.STRENGTH_SAP, Moves.SALT_CURE ], [Species.CORSOLA]: [ Moves.SCALD, Moves.FREEZE_DRY, Moves.STRENGTH_SAP, Moves.SALT_CURE ],
[Species.REMORAID]: [ Moves.WATER_SHURIKEN, Moves.TAKE_HEART, Moves.SHELL_SIDE_ARM, Moves.BOUNCY_BUBBLE ], [Species.REMORAID]: [ Moves.WATER_SHURIKEN, Moves.TAKE_HEART, Moves.SHELL_SIDE_ARM, Moves.BOUNCY_BUBBLE ],
[Species.DELIBIRD]: [ Moves.BONEMERANG, Moves.FLOATY_FALL, Moves.VICTORY_DANCE, Moves.GLACIAL_LANCE ], [Species.DELIBIRD]: [ Moves.BONEMERANG, Moves.FLOATY_FALL, Moves.VICTORY_DANCE, Moves.GLACIAL_LANCE ],
[Species.SKARMORY]: [ Moves.ROOST, Moves.BODY_PRESS, Moves.SPIKY_SHIELD, Moves.BEAK_BLAST ], [Species.SKARMORY]: [ Moves.ROOST, Moves.BODY_PRESS, Moves.SPIKY_SHIELD, Moves.BEAK_BLAST ],
[Species.HOUNDOUR]: [ Moves.MOONLIGHT, Moves.FIERY_WRATH, Moves.SECRET_SWORD, Moves.HYDRO_STEAM ], [Species.HOUNDOUR]: [ Moves.EARTH_POWER, Moves.THUNDERBOLT, Moves.MOONBLAST, Moves.FIERY_WRATH ],
[Species.PHANPY]: [ Moves.SHORE_UP, Moves.SWORDS_DANCE, Moves.ICICLE_CRASH, Moves.COLLISION_COURSE ], [Species.PHANPY]: [ Moves.SHORE_UP, Moves.SWORDS_DANCE, Moves.MOUNTAIN_GALE, Moves.COLLISION_COURSE ],
[Species.STANTLER]: [ Moves.THUNDEROUS_KICK, Moves.PHOTON_GEYSER, Moves.SWORDS_DANCE, Moves.BOOMBURST ], [Species.STANTLER]: [ Moves.THUNDEROUS_KICK, Moves.PHOTON_GEYSER, Moves.SWORDS_DANCE, Moves.BOOMBURST ],
[Species.SMEARGLE]: [ Moves.CONVERSION, Moves.BURNING_BULWARK, Moves.SALT_CURE, Moves.DARK_VOID ], [Species.SMEARGLE]: [ Moves.CONVERSION, Moves.BURNING_BULWARK, Moves.SALT_CURE, Moves.DARK_VOID ],
[Species.TYROGUE]: [ Moves.VICTORY_DANCE, Moves.THUNDEROUS_KICK, Moves.METEOR_MASH, Moves.WICKED_BLOW ], [Species.TYROGUE]: [ Moves.VICTORY_DANCE, Moves.THUNDEROUS_KICK, Moves.METEOR_MASH, Moves.WICKED_BLOW ],
[Species.SMOOCHUM]: [ Moves.EXPANDING_FORCE, Moves.AURA_SPHERE, Moves.FREEZE_DRY, Moves.QUIVER_DANCE ], [Species.SMOOCHUM]: [ Moves.LUSTER_PURGE, Moves.AURA_SPHERE, Moves.FREEZE_DRY, Moves.QUIVER_DANCE ],
[Species.ELEKID]: [ Moves.FIRE_LASH, Moves.ZING_ZAP, Moves.MOUNTAIN_GALE, Moves.SHIFT_GEAR ], [Species.ELEKID]: [ Moves.FIRE_LASH, Moves.ZING_ZAP, Moves.MOUNTAIN_GALE, Moves.SHIFT_GEAR ],
[Species.MAGBY]: [ Moves.THUNDERCLAP, Moves.EARTH_POWER, Moves.ARMOR_CANNON, Moves.FLEUR_CANNON ], [Species.MAGBY]: [ Moves.THUNDERCLAP, Moves.EARTH_POWER, Moves.ENERGY_BALL, Moves.BLUE_FLARE ],
[Species.MILTANK]: [ Moves.BODY_PRESS, Moves.BULK_UP, Moves.YAWN, Moves.SIZZLY_SLIDE ], [Species.MILTANK]: [ Moves.BODY_PRESS, Moves.BULK_UP, Moves.KNOCK_OFF, Moves.SIZZLY_SLIDE ],
[Species.RAIKOU]: [ Moves.PARABOLIC_CHARGE, Moves.NASTY_PLOT, Moves.FROST_BREATH, Moves.ELECTRO_DRIFT ], [Species.RAIKOU]: [ Moves.PARABOLIC_CHARGE, Moves.NASTY_PLOT, Moves.FROST_BREATH, Moves.ELECTRO_DRIFT ],
[Species.ENTEI]: [ Moves.BURNING_BULWARK, Moves.DRAGON_DANCE, Moves.EARTHQUAKE, Moves.MIGHTY_CLEAVE ], [Species.ENTEI]: [ Moves.BURNING_BULWARK, Moves.DRAGON_DANCE, Moves.EARTHQUAKE, Moves.PYRO_BALL ],
[Species.SUICUNE]: [ Moves.RECOVER, Moves.NASTY_PLOT, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ], [Species.SUICUNE]: [ Moves.RECOVER, Moves.NASTY_PLOT, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ],
[Species.LARVITAR]: [ Moves.DRAGON_DANCE, Moves.MOUNTAIN_GALE, Moves.SHORE_UP, Moves.DIAMOND_STORM ], [Species.LARVITAR]: [ Moves.DRAGON_DANCE, Moves.MOUNTAIN_GALE, Moves.SHORE_UP, Moves.DIAMOND_STORM ],
[Species.LUGIA]: [ Moves.NASTY_PLOT, Moves.LUMINA_CRASH, Moves.AURA_SPHERE, Moves.OBLIVION_WING ], [Species.LUGIA]: [ Moves.NASTY_PLOT, Moves.LUMINA_CRASH, Moves.AURA_SPHERE, Moves.OBLIVION_WING ],
[Species.HO_OH]: [ Moves.BRAVE_BIRD, Moves.DRAGON_DANCE, Moves.REVIVAL_BLESSING, Moves.BOLT_BEAK ], [Species.HO_OH]: [ Moves.BRAVE_BIRD, Moves.DRAGON_DANCE, Moves.REVIVAL_BLESSING, Moves.BOLT_BEAK ],
[Species.CELEBI]: [ Moves.PHOTON_GEYSER, Moves.MATCHA_GOTCHA, Moves.REVIVAL_BLESSING, Moves.QUIVER_DANCE ], [Species.CELEBI]: [ Moves.PHOTON_GEYSER, Moves.MATCHA_GOTCHA, Moves.REVIVAL_BLESSING, Moves.QUIVER_DANCE ],
[Species.TREECKO]: [ Moves.NASTY_PLOT, Moves.APPLE_ACID, Moves.SECRET_SWORD, Moves.DRAGON_ENERGY ],
[Species.TORCHIC]: [ Moves.HIGH_JUMP_KICK, Moves.SUPERCELL_SLAM, Moves.BURNING_BULWARK, Moves.V_CREATE ], [Species.TREECKO]: [ Moves.NASTY_PLOT, Moves.CORE_ENFORCER, Moves.FLAMETHROWER, Moves.SEED_FLARE ],
[Species.MUDKIP]: [ Moves.SHORE_UP, Moves.MOUNTAIN_GALE, Moves.BULK_UP, Moves.SURGING_STRIKES ], [Species.TORCHIC]: [ Moves.THUNDEROUS_KICK, Moves.ZING_ZAP, Moves.BURNING_BULWARK, Moves.PYRO_BALL ],
[Species.MUDKIP]: [ Moves.SHORE_UP, Moves.MOUNTAIN_GALE, Moves.AQUA_STEP, Moves.PRECIPICE_BLADES ],
[Species.POOCHYENA]: [ Moves.JAW_LOCK, Moves.CLOSE_COMBAT, Moves.DIRE_CLAW, Moves.NO_RETREAT ], [Species.POOCHYENA]: [ Moves.JAW_LOCK, Moves.CLOSE_COMBAT, Moves.DIRE_CLAW, Moves.NO_RETREAT ],
[Species.ZIGZAGOON]: [ Moves.EXTREME_SPEED, Moves.NUZZLE, Moves.HIGH_HORSEPOWER, Moves.TIDY_UP ], [Species.ZIGZAGOON]: [ Moves.EXTREME_SPEED, Moves.NUZZLE, Moves.HIGH_HORSEPOWER, Moves.TIDY_UP ],
[Species.WURMPLE]: [ Moves.BATON_PASS, Moves.BLEAKWIND_STORM, Moves.STORED_POWER, Moves.MALIGNANT_CHAIN ], [Species.WURMPLE]: [ Moves.BATON_PASS, Moves.BLEAKWIND_STORM, Moves.STORED_POWER, Moves.MALIGNANT_CHAIN ],
@ -151,35 +153,35 @@ export const speciesEggMoves = {
[Species.MAWILE]: [ Moves.BULLET_PUNCH, Moves.MAGICAL_TORQUE, Moves.EARTHQUAKE, Moves.SHIFT_GEAR ], [Species.MAWILE]: [ Moves.BULLET_PUNCH, Moves.MAGICAL_TORQUE, Moves.EARTHQUAKE, Moves.SHIFT_GEAR ],
[Species.ARON]: [ Moves.HEAD_SMASH, Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SALT_CURE ], [Species.ARON]: [ Moves.HEAD_SMASH, Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SALT_CURE ],
[Species.MEDITITE]: [ Moves.THUNDEROUS_KICK, Moves.SUCKER_PUNCH, Moves.BULLET_PUNCH, Moves.PHOTON_GEYSER ], [Species.MEDITITE]: [ Moves.THUNDEROUS_KICK, Moves.SUCKER_PUNCH, Moves.BULLET_PUNCH, Moves.PHOTON_GEYSER ],
[Species.ELECTRIKE]: [ Moves.RISING_VOLTAGE, Moves.FLAMETHROWER, Moves.NASTY_PLOT, Moves.ICE_BEAM ], [Species.ELECTRIKE]: [ Moves.FROST_BREATH, Moves.HEAT_WAVE, Moves.NASTY_PLOT, Moves.ELECTRO_DRIFT ],
[Species.PLUSLE]: [ Moves.FLAMETHROWER, Moves.GLITZY_GLOW, Moves.SPLISHY_SPLASH, Moves.TAIL_GLOW ], [Species.PLUSLE]: [ Moves.FLAMETHROWER, Moves.GLITZY_GLOW, Moves.SPLISHY_SPLASH, Moves.TAIL_GLOW ],
[Species.MINUN]: [ Moves.ICE_BEAM, Moves.BADDY_BAD, Moves.SPARKLY_SWIRL, Moves.TAIL_GLOW ], [Species.MINUN]: [ Moves.ICE_BEAM, Moves.BADDY_BAD, Moves.SPARKLY_SWIRL, Moves.TAIL_GLOW ],
[Species.VOLBEAT]: [ Moves.BATON_PASS, Moves.STICKY_WEB, Moves.DECORATE, Moves.VICTORY_DANCE ], [Species.VOLBEAT]: [ Moves.BATON_PASS, Moves.STICKY_WEB, Moves.DECORATE, Moves.VICTORY_DANCE ],
[Species.ILLUMISE]: [ Moves.PARTING_SHOT, Moves.GLITZY_GLOW, Moves.POWDER, Moves.QUIVER_DANCE ], [Species.ILLUMISE]: [ Moves.PARTING_SHOT, Moves.GLITZY_GLOW, Moves.POWDER, Moves.QUIVER_DANCE ],
[Species.GULPIN]: [ Moves.STRENGTH_SAP, Moves.EARTH_POWER, Moves.CALM_MIND, Moves.MALIGNANT_CHAIN ], [Species.GULPIN]: [ Moves.MALIGNANT_CHAIN, Moves.EARTH_POWER, Moves.CALM_MIND, Moves.STRENGTH_SAP ],
[Species.CARVANHA]: [ Moves.THUNDER_FANG, Moves.SWORDS_DANCE, Moves.OBSTRUCT, Moves.SURGING_STRIKES ], [Species.CARVANHA]: [ Moves.THUNDER_FANG, Moves.SWORDS_DANCE, Moves.OBSTRUCT, Moves.SURGING_STRIKES ],
[Species.WAILMER]: [ Moves.TAKE_HEART, Moves.BOUNCY_BUBBLE, Moves.SLACK_OFF, Moves.COMEUPPANCE ], [Species.WAILMER]: [ Moves.TAKE_HEART, Moves.COMEUPPANCE, Moves.SLACK_OFF, Moves.STEAM_ERUPTION ],
[Species.NUMEL]: [ Moves.TRICK_ROOM, Moves.ENERGY_BALL, Moves.MORNING_SUN, Moves.BLUE_FLARE ], [Species.NUMEL]: [ Moves.TRICK_ROOM, Moves.ENERGY_BALL, Moves.SLACK_OFF, Moves.BLUE_FLARE ],
[Species.TORKOAL]: [ Moves.MORNING_SUN, Moves.BURNING_BULWARK, Moves.BODY_PRESS, Moves.HYDRO_STEAM ], [Species.TORKOAL]: [ Moves.MORNING_SUN, Moves.BURNING_BULWARK, Moves.BODY_PRESS, Moves.HYDRO_STEAM ],
[Species.SPOINK]: [ Moves.AURA_SPHERE, Moves.MILK_DRINK, Moves.EXPANDING_FORCE, Moves.TAIL_GLOW ], [Species.SPOINK]: [ Moves.AURA_SPHERE, Moves.MILK_DRINK, Moves.EXPANDING_FORCE, Moves.TAIL_GLOW ],
[Species.SPINDA]: [ Moves.SUPERPOWER, Moves.SLACK_OFF, Moves.FLEUR_CANNON, Moves.V_CREATE ], [Species.SPINDA]: [ Moves.SUPERPOWER, Moves.SLACK_OFF, Moves.FLEUR_CANNON, Moves.V_CREATE ],
[Species.TRAPINCH]: [ Moves.FIRE_LASH, Moves.DRAGON_DARTS, Moves.THOUSAND_ARROWS, Moves.DRAGON_ENERGY ], [Species.TRAPINCH]: [ Moves.FIRE_LASH, Moves.DRAGON_DARTS, Moves.THOUSAND_ARROWS, Moves.DRAGON_ENERGY ],
[Species.CACNEA]: [ Moves.EARTH_POWER, Moves.CEASELESS_EDGE, Moves.NIGHT_DAZE, Moves.IVY_CUDGEL ], [Species.CACNEA]: [ Moves.EARTH_POWER, Moves.CEASELESS_EDGE, Moves.NIGHT_DAZE, Moves.SAPPY_SEED ],
[Species.SWABLU]: [ Moves.ROOST, Moves.NASTY_PLOT, Moves.FLOATY_FALL, Moves.BOOMBURST ], [Species.SWABLU]: [ Moves.ROOST, Moves.NASTY_PLOT, Moves.FLOATY_FALL, Moves.BOOMBURST ],
[Species.ZANGOOSE]: [ Moves.FACADE, Moves.HIGH_HORSEPOWER, Moves.EXTREME_SPEED, Moves.TIDY_UP ], [Species.ZANGOOSE]: [ Moves.FACADE, Moves.HIGH_HORSEPOWER, Moves.EXTREME_SPEED, Moves.TIDY_UP ],
[Species.SEVIPER]: [ Moves.ICE_BEAM, Moves.BITTER_BLADE, Moves.SUCKER_PUNCH, Moves.NO_RETREAT ], [Species.SEVIPER]: [ Moves.ICE_BEAM, Moves.BITTER_BLADE, Moves.SUCKER_PUNCH, Moves.NO_RETREAT ],
[Species.LUNATONE]: [ Moves.POWER_GEM, Moves.MOONGEIST_BEAM, Moves.SHELL_SMASH, Moves.LUMINA_CRASH ], [Species.LUNATONE]: [ Moves.REVELATION_DANCE, Moves.MOONGEIST_BEAM, Moves.SHELL_SMASH, Moves.LUMINA_CRASH ],
[Species.SOLROCK]: [ Moves.PSYSHIELD_BASH, Moves.MIGHTY_CLEAVE, Moves.SHELL_SMASH, Moves.SACRED_FIRE ], [Species.SOLROCK]: [ Moves.MIGHTY_CLEAVE, Moves.PHOTON_GEYSER, Moves.SHELL_SMASH, Moves.SACRED_FIRE ],
[Species.BARBOACH]: [ Moves.DRAGON_DANCE, Moves.ZING_ZAP, Moves.ICE_SPINNER, Moves.SURGING_STRIKES ], [Species.BARBOACH]: [ Moves.DRAGON_DANCE, Moves.ZING_ZAP, Moves.ICE_SPINNER, Moves.SURGING_STRIKES ],
[Species.CORPHISH]: [ Moves.CEASELESS_EDGE, Moves.JET_PUNCH, Moves.SUCKER_PUNCH, Moves.SHELL_SMASH ], [Species.CORPHISH]: [ Moves.CEASELESS_EDGE, Moves.SHELL_SIDE_ARM, Moves.SUCKER_PUNCH, Moves.JET_PUNCH ],
[Species.BALTOY]: [ Moves.RECOVER, Moves.STORED_POWER, Moves.BODY_PRESS, Moves.MYSTICAL_POWER ], [Species.BALTOY]: [ Moves.RECOVER, Moves.GLARE, Moves.RUINATION, Moves.MYSTICAL_POWER ],
[Species.LILEEP]: [ Moves.POWER_GEM, Moves.SCALD, Moves.STRENGTH_SAP, Moves.SAPPY_SEED ], [Species.LILEEP]: [ Moves.POWER_GEM, Moves.SCALD, Moves.STRENGTH_SAP, Moves.SAPPY_SEED ],
[Species.ANORITH]: [ Moves.FIRST_IMPRESSION, Moves.LEECH_LIFE, Moves.DRAGON_DANCE, Moves.MIGHTY_CLEAVE ], [Species.ANORITH]: [ Moves.FIRST_IMPRESSION, Moves.LEECH_LIFE, Moves.DRAGON_DANCE, Moves.MIGHTY_CLEAVE ],
[Species.FEEBAS]: [ Moves.CALM_MIND, Moves.FREEZE_DRY, Moves.MOONBLAST, Moves.STEAM_ERUPTION ], [Species.FEEBAS]: [ Moves.CALM_MIND, Moves.FREEZE_DRY, Moves.MOONBLAST, Moves.STEAM_ERUPTION ],
[Species.CASTFORM]: [ Moves.BOOMBURST, Moves.HYDRO_STEAM, Moves.ERUPTION, Moves.QUIVER_DANCE ], [Species.CASTFORM]: [ Moves.BOOMBURST, Moves.HYDRO_STEAM, Moves.ERUPTION, Moves.QUIVER_DANCE ],
[Species.KECLEON]: [ Moves.ZIPPY_ZAP, Moves.COIL, Moves.EXTREME_SPEED, Moves.MULTI_ATTACK ], [Species.KECLEON]: [ Moves.ZIPPY_ZAP, Moves.COIL, Moves.EXTREME_SPEED, Moves.MULTI_ATTACK ],
[Species.SHUPPET]: [ Moves.STORM_THROW, Moves.TIDY_UP, Moves.PARTING_SHOT, Moves.SPECTRAL_THIEF ], [Species.SHUPPET]: [ Moves.STORM_THROW, Moves.TIDY_UP, Moves.PARTING_SHOT, Moves.SPECTRAL_THIEF ],
[Species.DUSKULL]: [ Moves.BULK_UP, Moves.DRAIN_PUNCH, Moves.STRENGTH_SAP, Moves.RAGE_FIST ], [Species.DUSKULL]: [ Moves.BULK_UP, Moves.DRAIN_PUNCH, Moves.RECOVER, Moves.RAGE_FIST ],
[Species.TROPIUS]: [ Moves.STUFF_CHEEKS, Moves.EARTH_POWER, Moves.APPLE_ACID, Moves.SAPPY_SEED ], [Species.TROPIUS]: [ Moves.STUFF_CHEEKS, Moves.EARTH_POWER, Moves.APPLE_ACID, Moves.SAPPY_SEED ],
[Species.ABSOL]: [ Moves.KOWTOW_CLEAVE, Moves.SACRED_SWORD, Moves.PSYBLADE, Moves.BITTER_BLADE ], [Species.ABSOL]: [ Moves.KOWTOW_CLEAVE, Moves.SACRED_SWORD, Moves.PSYBLADE, Moves.BITTER_BLADE ],
[Species.WYNAUT]: [ Moves.RECOVER, Moves.SHED_TAIL, Moves.TAUNT, Moves.COMEUPPANCE ], [Species.WYNAUT]: [ Moves.RECOVER, Moves.SHED_TAIL, Moves.TAUNT, Moves.COMEUPPANCE ],
@ -188,21 +190,22 @@ export const speciesEggMoves = {
[Species.CLAMPERL]: [ Moves.SHELL_SIDE_ARM, Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ], [Species.CLAMPERL]: [ Moves.SHELL_SIDE_ARM, Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ],
[Species.RELICANTH]: [ Moves.DRAGON_DANCE, Moves.SHORE_UP, Moves.WAVE_CRASH, Moves.DIAMOND_STORM ], [Species.RELICANTH]: [ Moves.DRAGON_DANCE, Moves.SHORE_UP, Moves.WAVE_CRASH, Moves.DIAMOND_STORM ],
[Species.LUVDISC]: [ Moves.BATON_PASS, Moves.HEART_SWAP, Moves.GLITZY_GLOW, Moves.REVIVAL_BLESSING ], [Species.LUVDISC]: [ Moves.BATON_PASS, Moves.HEART_SWAP, Moves.GLITZY_GLOW, Moves.REVIVAL_BLESSING ],
[Species.BAGON]: [ Moves.FLOATY_FALL, Moves.FIRE_LASH, Moves.DRAGON_DANCE, Moves.GLAIVE_RUSH ], [Species.BAGON]: [ Moves.FLOATY_FALL, Moves.FIRE_LASH, Moves.DRAGON_DANCE, Moves.DRAGON_DARTS ],
[Species.BELDUM]: [ Moves.HEADLONG_RUSH, Moves.DRAIN_PUNCH, Moves.TRIPLE_AXEL, Moves.SHIFT_GEAR ], [Species.BELDUM]: [ Moves.HEADLONG_RUSH, Moves.DRAIN_PUNCH, Moves.TRIPLE_AXEL, Moves.SHIFT_GEAR ],
[Species.REGIROCK]: [ Moves.STONE_AXE, Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SALT_CURE ], [Species.REGIROCK]: [ Moves.STONE_AXE, Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SALT_CURE ],
[Species.REGICE]: [ Moves.EARTH_POWER, Moves.TAKE_HEART, Moves.RECOVER, Moves.FREEZE_DRY ], [Species.REGICE]: [ Moves.EARTH_POWER, Moves.TAKE_HEART, Moves.RECOVER, Moves.FREEZE_DRY ],
[Species.REGISTEEL]: [ Moves.BODY_PRESS, Moves.SIZZLY_SLIDE, Moves.RECOVER, Moves.GIGATON_HAMMER ], [Species.REGISTEEL]: [ Moves.BODY_PRESS, Moves.SIZZLY_SLIDE, Moves.RECOVER, Moves.GIGATON_HAMMER ],
[Species.LATIAS]: [ Moves.CORE_ENFORCER, Moves.FUSION_FLARE, Moves.SPARKLY_SWIRL, Moves.MYSTICAL_POWER ], [Species.LATIAS]: [ Moves.CORE_ENFORCER, Moves.FUSION_FLARE, Moves.SPARKLY_SWIRL, Moves.MYSTICAL_POWER ],
[Species.LATIOS]: [ Moves.CORE_ENFORCER, Moves.BLUE_FLARE, Moves.NASTY_PLOT, Moves.TACHYON_CUTTER ], [Species.LATIOS]: [ Moves.CORE_ENFORCER, Moves.BLUE_FLARE, Moves.NASTY_PLOT, Moves.TACHYON_CUTTER ],
[Species.KYOGRE]: [ Moves.RECOVER, Moves.HURRICANE, Moves.FREEZY_FROST, Moves.WILDBOLT_STORM ], [Species.KYOGRE]: [ Moves.WILDBOLT_STORM, Moves.HURRICANE, Moves.FREEZY_FROST, Moves.BOUNCY_BUBBLE ],
[Species.GROUDON]: [ Moves.STONE_AXE, Moves.SOLAR_BLADE, Moves.MORNING_SUN, Moves.SACRED_FIRE ], [Species.GROUDON]: [ Moves.STONE_AXE, Moves.SOLAR_BLADE, Moves.MORNING_SUN, Moves.SACRED_FIRE ],
[Species.RAYQUAZA]: [ Moves.V_CREATE, Moves.DRAGON_DARTS, Moves.CORE_ENFORCER, Moves.OBLIVION_WING ], [Species.RAYQUAZA]: [ Moves.V_CREATE, Moves.DRAGON_DARTS, Moves.CORE_ENFORCER, Moves.OBLIVION_WING ],
[Species.JIRACHI]: [ Moves.TACHYON_CUTTER, Moves.TRIPLE_ARROWS, Moves.ROCK_SLIDE, Moves.SHELL_SMASH ], [Species.JIRACHI]: [ Moves.TACHYON_CUTTER, Moves.TRIPLE_ARROWS, Moves.ROCK_SLIDE, Moves.SHELL_SMASH ],
[Species.DEOXYS]: [ Moves.COLLISION_COURSE, Moves.EARTH_POWER, Moves.PARTING_SHOT, Moves.LUMINA_CRASH ], [Species.DEOXYS]: [ Moves.COLLISION_COURSE, Moves.FUSION_FLARE, Moves.PARTING_SHOT, Moves.LUMINA_CRASH ],
[Species.TURTWIG]: [ Moves.SHELL_SMASH, Moves.MIGHTY_CLEAVE, Moves.ICE_SPINNER, Moves.SAPPY_SEED ], [Species.TURTWIG]: [ Moves.SHELL_SMASH, Moves.MIGHTY_CLEAVE, Moves.ICE_SPINNER, Moves.SAPPY_SEED ],
[Species.CHIMCHAR]: [ Moves.FIERY_DANCE, Moves.SECRET_SWORD, Moves.TRIPLE_AXEL, Moves.SACRED_FIRE ], [Species.CHIMCHAR]: [ Moves.FIERY_DANCE, Moves.SECRET_SWORD, Moves.TRIPLE_AXEL, Moves.SACRED_FIRE ],
[Species.PIPLUP]: [ Moves.KINGS_SHIELD, Moves.TACHYON_CUTTER, Moves.ROOST, Moves.STEAM_ERUPTION ], [Species.PIPLUP]: [ Moves.KINGS_SHIELD, Moves.TACHYON_CUTTER, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ],
[Species.STARLY]: [ Moves.SWORDS_DANCE, Moves.HEAD_CHARGE, Moves.FLARE_BLITZ, Moves.EXTREME_SPEED ], [Species.STARLY]: [ Moves.SWORDS_DANCE, Moves.HEAD_CHARGE, Moves.FLARE_BLITZ, Moves.EXTREME_SPEED ],
[Species.BIDOOF]: [ Moves.EXTREME_SPEED, Moves.COSMIC_POWER, Moves.POWER_TRIP, Moves.AQUA_STEP ], [Species.BIDOOF]: [ Moves.EXTREME_SPEED, Moves.COSMIC_POWER, Moves.POWER_TRIP, Moves.AQUA_STEP ],
[Species.KRICKETOT]: [ Moves.BONEMERANG, Moves.VICTORY_DANCE, Moves.STONE_AXE, Moves.POPULATION_BOMB ], [Species.KRICKETOT]: [ Moves.BONEMERANG, Moves.VICTORY_DANCE, Moves.STONE_AXE, Moves.POPULATION_BOMB ],
@ -214,7 +217,7 @@ export const speciesEggMoves = {
[Species.COMBEE]: [ Moves.SPORE, Moves.FLOATY_FALL, Moves.KINGS_SHIELD, Moves.VICTORY_DANCE ], [Species.COMBEE]: [ Moves.SPORE, Moves.FLOATY_FALL, Moves.KINGS_SHIELD, Moves.VICTORY_DANCE ],
[Species.PACHIRISU]: [ Moves.FREEZY_FROST, Moves.SIZZLY_SLIDE, Moves.SLACK_OFF, Moves.ZIPPY_ZAP ], [Species.PACHIRISU]: [ Moves.FREEZY_FROST, Moves.SIZZLY_SLIDE, Moves.SLACK_OFF, Moves.ZIPPY_ZAP ],
[Species.BUIZEL]: [ Moves.JET_PUNCH, Moves.TRIPLE_AXEL, Moves.SUPERCELL_SLAM, Moves.SURGING_STRIKES ], [Species.BUIZEL]: [ Moves.JET_PUNCH, Moves.TRIPLE_AXEL, Moves.SUPERCELL_SLAM, Moves.SURGING_STRIKES ],
[Species.CHERUBI]: [ Moves.SPORE, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.FLOWER_TRICK ], [Species.CHERUBI]: [ Moves.SLEEP_POWDER, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.FLOWER_TRICK ],
[Species.SHELLOS]: [ Moves.BOUNCY_BUBBLE, Moves.SCORCHING_SANDS, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ], [Species.SHELLOS]: [ Moves.BOUNCY_BUBBLE, Moves.SCORCHING_SANDS, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ],
[Species.DRIFLOON]: [ Moves.WILL_O_WISP, Moves.MIND_BLOWN, Moves.CALM_MIND, Moves.OBLIVION_WING ], [Species.DRIFLOON]: [ Moves.WILL_O_WISP, Moves.MIND_BLOWN, Moves.CALM_MIND, Moves.OBLIVION_WING ],
[Species.BUNEARY]: [ Moves.TRIPLE_AXEL, Moves.SWORDS_DANCE, Moves.THUNDEROUS_KICK, Moves.MULTI_ATTACK ], [Species.BUNEARY]: [ Moves.TRIPLE_AXEL, Moves.SWORDS_DANCE, Moves.THUNDEROUS_KICK, Moves.MULTI_ATTACK ],
@ -225,36 +228,37 @@ export const speciesEggMoves = {
[Species.BONSLY]: [ Moves.ACCELEROCK, Moves.SWORDS_DANCE, Moves.STRENGTH_SAP, Moves.SAPPY_SEED ], [Species.BONSLY]: [ Moves.ACCELEROCK, Moves.SWORDS_DANCE, Moves.STRENGTH_SAP, Moves.SAPPY_SEED ],
[Species.MIME_JR]: [ Moves.CHILLY_RECEPTION, Moves.MOONBLAST, Moves.FROST_BREATH, Moves.LUMINA_CRASH ], [Species.MIME_JR]: [ Moves.CHILLY_RECEPTION, Moves.MOONBLAST, Moves.FROST_BREATH, Moves.LUMINA_CRASH ],
[Species.HAPPINY]: [ Moves.COTTON_GUARD, Moves.SEISMIC_TOSS, Moves.SIZZLY_SLIDE, Moves.REVIVAL_BLESSING ], [Species.HAPPINY]: [ Moves.COTTON_GUARD, Moves.SEISMIC_TOSS, Moves.SIZZLY_SLIDE, Moves.REVIVAL_BLESSING ],
[Species.CHATOT]: [ Moves.SPARKLING_ARIA, Moves.TORCH_SONG, Moves.BATON_PASS, Moves.BOOMBURST ], [Species.CHATOT]: [ Moves.SPARKLING_ARIA, Moves.BOOMBURST, Moves.BATON_PASS, Moves.TORCH_SONG ],
[Species.SPIRITOMB]: [ Moves.PARTING_SHOT, Moves.BADDY_BAD, Moves.STRENGTH_SAP, Moves.SPECTRAL_THIEF ], [Species.SPIRITOMB]: [ Moves.PARTING_SHOT, Moves.BADDY_BAD, Moves.STRENGTH_SAP, Moves.SPECTRAL_THIEF ],
[Species.GIBLE]: [ Moves.DRAGON_DANCE, Moves.BITTER_BLADE, Moves.SHORE_UP, Moves.THOUSAND_ARROWS ], [Species.GIBLE]: [ Moves.DRAGON_DANCE, Moves.BITTER_BLADE, Moves.DRAGON_HAMMER, Moves.PRECIPICE_BLADES ],
[Species.MUNCHLAX]: [ Moves.STUFF_CHEEKS, Moves.GRAV_APPLE, Moves.SLACK_OFF, Moves.EXTREME_SPEED ], [Species.MUNCHLAX]: [ Moves.STUFF_CHEEKS, Moves.GRAV_APPLE, Moves.SLACK_OFF, Moves.EXTREME_SPEED ],
[Species.RIOLU]: [ Moves.THUNDEROUS_KICK, Moves.TACHYON_CUTTER, Moves.TRIPLE_AXEL, Moves.DOUBLE_IRON_BASH ], [Species.RIOLU]: [ Moves.THUNDEROUS_KICK, Moves.TACHYON_CUTTER, Moves.TRIPLE_AXEL, Moves.SUNSTEEL_STRIKE ],
[Species.HIPPOPOTAS]: [ Moves.SHORE_UP, Moves.STONE_AXE, Moves.BULK_UP, Moves.SALT_CURE ], [Species.HIPPOPOTAS]: [ Moves.SHORE_UP, Moves.STONE_AXE, Moves.BULK_UP, Moves.SALT_CURE ],
[Species.SKORUPI]: [ Moves.COIL, Moves.DIRE_CLAW, Moves.CRABHAMMER, Moves.WICKED_BLOW ], [Species.SKORUPI]: [ Moves.COIL, Moves.DIRE_CLAW, Moves.CRABHAMMER, Moves.WICKED_BLOW ],
[Species.CROAGUNK]: [ Moves.DIRE_CLAW, Moves.ICE_SPINNER, Moves.THUNDEROUS_KICK, Moves.VICTORY_DANCE ], [Species.CROAGUNK]: [ Moves.DIRE_CLAW, Moves.ICE_SPINNER, Moves.THUNDEROUS_KICK, Moves.VICTORY_DANCE ],
[Species.CARNIVINE]: [ Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.COIL, Moves.SAPPY_SEED ], [Species.CARNIVINE]: [ Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.COIL, Moves.SAPPY_SEED ],
[Species.FINNEON]: [ Moves.QUIVER_DANCE, Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.ORIGIN_PULSE ], [Species.FINNEON]: [ Moves.QUIVER_DANCE, Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.ORIGIN_PULSE ],
[Species.MANTYKE]: [ Moves.SPLISHY_SPLASH, Moves.FREEZY_FROST, Moves.NASTY_PLOT, Moves.OBLIVION_WING ], [Species.MANTYKE]: [ Moves.SPLISHY_SPLASH, Moves.FREEZY_FROST, Moves.NASTY_PLOT, Moves.OBLIVION_WING ],
[Species.SNOVER]: [ Moves.HIGH_HORSEPOWER, Moves.STRENGTH_SAP, Moves.MATCHA_GOTCHA, Moves.SAPPY_SEED ], [Species.SNOVER]: [ Moves.LANDS_WRATH, Moves.POWDER, Moves.CALM_MIND, Moves.MATCHA_GOTCHA ],
[Species.ROTOM]: [ Moves.STRENGTH_SAP, Moves.FIERY_DANCE, Moves.SPLISHY_SPLASH, Moves.ELECTRO_DRIFT ], [Species.ROTOM]: [ Moves.STRENGTH_SAP, Moves.FIERY_DANCE, Moves.SPLISHY_SPLASH, Moves.ELECTRO_DRIFT ],
[Species.UXIE]: [ Moves.COSMIC_POWER, Moves.BODY_PRESS, Moves.RECOVER, Moves.SPARKLY_SWIRL ], [Species.UXIE]: [ Moves.COSMIC_POWER, Moves.SECRET_SWORD, Moves.RECOVER, Moves.SPARKLY_SWIRL ],
[Species.MESPRIT]: [ Moves.TAIL_GLOW, Moves.AURA_SPHERE, Moves.RECOVER, Moves.LUMINA_CRASH ], [Species.MESPRIT]: [ Moves.TAIL_GLOW, Moves.AURA_SPHERE, Moves.RECOVER, Moves.LUMINA_CRASH ],
[Species.AZELF]: [ Moves.PSYSTRIKE, Moves.ICE_BEAM, Moves.MOONBLAST, Moves.TAIL_GLOW ], [Species.AZELF]: [ Moves.PSYSTRIKE, Moves.ICE_BEAM, Moves.MOONBLAST, Moves.TAIL_GLOW ],
[Species.DIALGA]: [ Moves.CORE_ENFORCER, Moves.TAKE_HEART, Moves.RECOVER, Moves.MAKE_IT_RAIN ], [Species.DIALGA]: [ Moves.CORE_ENFORCER, Moves.TAKE_HEART, Moves.RECOVER, Moves.MAKE_IT_RAIN ],
[Species.PALKIA]: [ Moves.RECOVER, Moves.TAKE_HEART, Moves.FREEZE_DRY, Moves.ORIGIN_PULSE ], [Species.PALKIA]: [ Moves.MALIGNANT_CHAIN, Moves.TAKE_HEART, Moves.RECOVER, Moves.ORIGIN_PULSE ],
[Species.HEATRAN]: [ Moves.MATCHA_GOTCHA, Moves.RECOVER, Moves.TACHYON_CUTTER, Moves.TORCH_SONG ], [Species.HEATRAN]: [ Moves.MATCHA_GOTCHA, Moves.RECOVER, Moves.ERUPTION, Moves.TACHYON_CUTTER ],
[Species.REGIGIGAS]: [ Moves.SKILL_SWAP, Moves.RECOVER, Moves.EXTREME_SPEED, Moves.GIGATON_HAMMER ], [Species.REGIGIGAS]: [ Moves.SKILL_SWAP, Moves.RECOVER, Moves.EXTREME_SPEED, Moves.GIGATON_HAMMER ],
[Species.GIRATINA]: [ Moves.DRAGON_DANCE, Moves.GLAIVE_RUSH, Moves.RECOVER, Moves.SPECTRAL_THIEF ], [Species.GIRATINA]: [ Moves.DRAGON_DANCE, Moves.GLAIVE_RUSH, Moves.RECOVER, Moves.SPECTRAL_THIEF ],
[Species.CRESSELIA]: [ Moves.COSMIC_POWER, Moves.SECRET_SWORD, Moves.SIZZLY_SLIDE, Moves.LUMINA_CRASH ], [Species.CRESSELIA]: [ Moves.COSMIC_POWER, Moves.BODY_PRESS, Moves.SIZZLY_SLIDE, Moves.LUMINA_CRASH ],
[Species.PHIONE]: [ Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.SPLISHY_SPLASH, Moves.QUIVER_DANCE ], [Species.PHIONE]: [ Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.STORED_POWER, Moves.ORIGIN_PULSE ],
[Species.MANAPHY]: [ Moves.BOUNCY_BUBBLE, Moves.FREEZE_DRY, Moves.SPLISHY_SPLASH, Moves.QUIVER_DANCE ], [Species.MANAPHY]: [ Moves.BOUNCY_BUBBLE, Moves.FROST_BREATH, Moves.WILDBOLT_STORM, Moves.ORIGIN_PULSE ],
[Species.DARKRAI]: [ Moves.FIERY_WRATH, Moves.MOONBLAST, Moves.FIERY_DANCE, Moves.MAKE_IT_RAIN ], [Species.DARKRAI]: [ Moves.FIERY_WRATH, Moves.MOONBLAST, Moves.FIERY_DANCE, Moves.MAKE_IT_RAIN ],
[Species.SHAYMIN]: [ Moves.MATCHA_GOTCHA, Moves.FIERY_DANCE, Moves.AEROBLAST, Moves.QUIVER_DANCE ], [Species.SHAYMIN]: [ Moves.MATCHA_GOTCHA, Moves.FIERY_DANCE, Moves.AEROBLAST, Moves.QUIVER_DANCE ],
[Species.ARCEUS]: [ Moves.NO_RETREAT, Moves.COLLISION_COURSE, Moves.ASTRAL_BARRAGE, Moves.MULTI_ATTACK ], [Species.ARCEUS]: [ Moves.NO_RETREAT, Moves.COLLISION_COURSE, Moves.ASTRAL_BARRAGE, Moves.MULTI_ATTACK ],
[Species.VICTINI]: [ Moves.BLUE_FLARE, Moves.BOLT_STRIKE, Moves.LUSTER_PURGE, Moves.VICTORY_DANCE ], [Species.VICTINI]: [ Moves.BLUE_FLARE, Moves.BOLT_STRIKE, Moves.LUSTER_PURGE, Moves.VICTORY_DANCE ],
[Species.SNIVY]: [ Moves.FLAMETHROWER, Moves.CLANGING_SCALES, Moves.MAKE_IT_RAIN, Moves.FLEUR_CANNON ], [Species.SNIVY]: [ Moves.FLAMETHROWER, Moves.CLANGING_SCALES, Moves.MAKE_IT_RAIN, Moves.FLEUR_CANNON ],
[Species.TEPIG]: [ Moves.WAVE_CRASH, Moves.VOLT_TACKLE, Moves.DRAIN_PUNCH, Moves.VICTORY_DANCE ], [Species.TEPIG]: [ Moves.WAVE_CRASH, Moves.VOLT_TACKLE, Moves.AXE_KICK, Moves.VICTORY_DANCE ],
[Species.OSHAWOTT]: [ Moves.TRIPLE_AXEL, Moves.SHELL_SIDE_ARM, Moves.SACRED_SWORD, Moves.SHELL_SMASH ], [Species.OSHAWOTT]: [ Moves.TRIPLE_AXEL, Moves.SHELL_SIDE_ARM, Moves.SACRED_SWORD, Moves.SHELL_SMASH ],
[Species.PATRAT]: [ Moves.FAKE_OUT, Moves.SWORDS_DANCE, Moves.DYNAMIC_PUNCH, Moves.EXTREME_SPEED ], [Species.PATRAT]: [ Moves.FAKE_OUT, Moves.SWORDS_DANCE, Moves.DYNAMIC_PUNCH, Moves.EXTREME_SPEED ],
[Species.LILLIPUP]: [ Moves.CLOSE_COMBAT, Moves.BODY_SLAM, Moves.HIGH_HORSEPOWER, Moves.LAST_RESPECTS ], [Species.LILLIPUP]: [ Moves.CLOSE_COMBAT, Moves.BODY_SLAM, Moves.HIGH_HORSEPOWER, Moves.LAST_RESPECTS ],
@ -262,13 +266,13 @@ export const speciesEggMoves = {
[Species.PANSAGE]: [ Moves.SWORDS_DANCE, Moves.FIRE_LASH, Moves.EARTHQUAKE, Moves.IVY_CUDGEL ], [Species.PANSAGE]: [ Moves.SWORDS_DANCE, Moves.FIRE_LASH, Moves.EARTHQUAKE, Moves.IVY_CUDGEL ],
[Species.PANSEAR]: [ Moves.NASTY_PLOT, Moves.HYDRO_STEAM, Moves.SCORCHING_SANDS, Moves.TORCH_SONG ], [Species.PANSEAR]: [ Moves.NASTY_PLOT, Moves.HYDRO_STEAM, Moves.SCORCHING_SANDS, Moves.TORCH_SONG ],
[Species.PANPOUR]: [ Moves.NASTY_PLOT, Moves.ENERGY_BALL, Moves.EARTH_POWER, Moves.STEAM_ERUPTION ], [Species.PANPOUR]: [ Moves.NASTY_PLOT, Moves.ENERGY_BALL, Moves.EARTH_POWER, Moves.STEAM_ERUPTION ],
[Species.MUNNA]: [ Moves.COSMIC_POWER, Moves.AURA_SPHERE, Moves.EARTH_POWER, Moves.MYSTICAL_POWER ], [Species.MUNNA]: [ Moves.COSMIC_POWER, Moves.AURA_SPHERE, Moves.LUNAR_BLESSING, Moves.MYSTICAL_POWER ],
[Species.PIDOVE]: [ Moves.GUNK_SHOT, Moves.TIDY_UP, Moves.FLOATY_FALL, Moves.TRIPLE_ARROWS ], [Species.PIDOVE]: [ Moves.GUNK_SHOT, Moves.TIDY_UP, Moves.FLOATY_FALL, Moves.TRIPLE_ARROWS ],
[Species.BLITZLE]: [ Moves.HORN_LEECH, Moves.SWORDS_DANCE, Moves.FLARE_BLITZ, Moves.BOLT_STRIKE ], [Species.BLITZLE]: [ Moves.HORN_LEECH, Moves.SWORDS_DANCE, Moves.FLARE_BLITZ, Moves.BOLT_STRIKE ],
[Species.ROGGENROLA]: [ Moves.BODY_PRESS, Moves.CURSE, Moves.SHORE_UP, Moves.DIAMOND_STORM ], [Species.ROGGENROLA]: [ Moves.BODY_PRESS, Moves.CURSE, Moves.SHORE_UP, Moves.DIAMOND_STORM ],
[Species.WOOBAT]: [ Moves.ESPER_WING, Moves.STORED_POWER, Moves.MYSTICAL_FIRE, Moves.OBLIVION_WING ], [Species.WOOBAT]: [ Moves.ESPER_WING, Moves.STORED_POWER, Moves.MYSTICAL_FIRE, Moves.OBLIVION_WING ],
[Species.DRILBUR]: [ Moves.IRON_HEAD, Moves.MOUNTAIN_GALE, Moves.SHIFT_GEAR, Moves.THOUSAND_ARROWS ], [Species.DRILBUR]: [ Moves.METEOR_MASH, Moves.MOUNTAIN_GALE, Moves.SHIFT_GEAR, Moves.PRECIPICE_BLADES ],
[Species.AUDINO]: [ Moves.FOLLOW_ME, Moves.MOONBLAST, Moves.WISH, Moves.LUNAR_BLESSING ], [Species.AUDINO]: [ Moves.TAKE_HEART, Moves.MOONBLAST, Moves.WISH, Moves.MATCHA_GOTCHA ],
[Species.TIMBURR]: [ Moves.MACH_PUNCH, Moves.DRAIN_PUNCH, Moves.ICE_HAMMER, Moves.DOUBLE_IRON_BASH ], [Species.TIMBURR]: [ Moves.MACH_PUNCH, Moves.DRAIN_PUNCH, Moves.ICE_HAMMER, Moves.DOUBLE_IRON_BASH ],
[Species.TYMPOLE]: [ Moves.JET_PUNCH, Moves.HIGH_HORSEPOWER, Moves.BULK_UP, Moves.SURGING_STRIKES ], [Species.TYMPOLE]: [ Moves.JET_PUNCH, Moves.HIGH_HORSEPOWER, Moves.BULK_UP, Moves.SURGING_STRIKES ],
[Species.THROH]: [ Moves.MACH_PUNCH, Moves.SLACK_OFF, Moves.METEOR_MASH, Moves.RAGE_FIST ], [Species.THROH]: [ Moves.MACH_PUNCH, Moves.SLACK_OFF, Moves.METEOR_MASH, Moves.RAGE_FIST ],
@ -278,41 +282,41 @@ export const speciesEggMoves = {
[Species.COTTONEE]: [ Moves.POLLEN_PUFF, Moves.PARTING_SHOT, Moves.SLEEP_POWDER, Moves.SEED_FLARE ], [Species.COTTONEE]: [ Moves.POLLEN_PUFF, Moves.PARTING_SHOT, Moves.SLEEP_POWDER, Moves.SEED_FLARE ],
[Species.PETILIL]: [ Moves.THUNDEROUS_KICK, Moves.SPARKLING_ARIA, Moves.FIERY_DANCE, Moves.FLOWER_TRICK ], [Species.PETILIL]: [ Moves.THUNDEROUS_KICK, Moves.SPARKLING_ARIA, Moves.FIERY_DANCE, Moves.FLOWER_TRICK ],
[Species.BASCULIN]: [ Moves.LAST_RESPECTS, Moves.CLOSE_COMBAT, Moves.SPLISHY_SPLASH, Moves.NO_RETREAT ], [Species.BASCULIN]: [ Moves.LAST_RESPECTS, Moves.CLOSE_COMBAT, Moves.SPLISHY_SPLASH, Moves.NO_RETREAT ],
[Species.SANDILE]: [ Moves.DIRE_CLAW, Moves.HIGH_HORSEPOWER, Moves.FIRE_LASH, Moves.WICKED_BLOW ], [Species.SANDILE]: [ Moves.DIRE_CLAW, Moves.HEADLONG_RUSH, Moves.FIRE_LASH, Moves.WICKED_BLOW ],
[Species.DARUMAKA]: [ Moves.DRAIN_PUNCH, Moves.ZIPPY_ZAP, Moves.EARTHQUAKE, Moves.PYRO_BALL ], [Species.DARUMAKA]: [ Moves.DRAIN_PUNCH, Moves.ZIPPY_ZAP, Moves.HEADLONG_RUSH, Moves.PYRO_BALL ],
[Species.MARACTUS]: [ Moves.EARTH_POWER, Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.SEED_FLARE ], [Species.MARACTUS]: [ Moves.EARTH_POWER, Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.SEED_FLARE ],
[Species.DWEBBLE]: [ Moves.CRABHAMMER, Moves.STONE_AXE, Moves.LEECH_LIFE, Moves.MIGHTY_CLEAVE ], [Species.DWEBBLE]: [ Moves.CRABHAMMER, Moves.STONE_AXE, Moves.LEECH_LIFE, Moves.MIGHTY_CLEAVE ],
[Species.SCRAGGY]: [ Moves.SUCKER_PUNCH, Moves.BULLET_PUNCH, Moves.NOXIOUS_TORQUE, Moves.VICTORY_DANCE ], [Species.SCRAGGY]: [ Moves.SUCKER_PUNCH, Moves.BULLET_PUNCH, Moves.NOXIOUS_TORQUE, Moves.VICTORY_DANCE ],
[Species.SIGILYPH]: [ Moves.MOONBLAST, Moves.CALM_MIND, Moves.FREEZING_GLARE, Moves.OBLIVION_WING ], [Species.SIGILYPH]: [ Moves.MOONBLAST, Moves.CALM_MIND, Moves.ESPER_WING, Moves.OBLIVION_WING ],
[Species.YAMASK]: [ Moves.STRENGTH_SAP, Moves.GLARE, Moves.AURA_SPHERE, Moves.ASTRAL_BARRAGE ], [Species.YAMASK]: [ Moves.STRENGTH_SAP, Moves.GLARE, Moves.AURA_SPHERE, Moves.ASTRAL_BARRAGE ],
[Species.TIRTOUGA]: [ Moves.ICE_SPINNER, Moves.AQUA_STEP, Moves.SHORE_UP, Moves.MIGHTY_CLEAVE ], [Species.TIRTOUGA]: [ Moves.ICE_SPINNER, Moves.AQUA_STEP, Moves.SHORE_UP, Moves.MIGHTY_CLEAVE ],
[Species.ARCHEN]: [ Moves.ROOST, Moves.EARTHQUAKE, Moves.FLOATY_FALL, Moves.MIGHTY_CLEAVE ], [Species.ARCHEN]: [ Moves.ROOST, Moves.EARTHQUAKE, Moves.FLOATY_FALL, Moves.MIGHTY_CLEAVE ],
[Species.TRUBBISH]: [ Moves.COIL, Moves.RECOVER, Moves.DIRE_CLAW, Moves.GIGATON_HAMMER ], [Species.TRUBBISH]: [ Moves.COIL, Moves.RECOVER, Moves.DIRE_CLAW, Moves.GIGATON_HAMMER ],
[Species.ZORUA]: [ Moves.FLAMETHROWER, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.FIERY_WRATH ], [Species.ZORUA]: [ Moves.MALIGNANT_CHAIN, Moves.MOONBLAST, Moves.SECRET_SWORD, Moves.FIERY_WRATH ],
[Species.MINCCINO]: [ Moves.ICICLE_SPEAR, Moves.TIDY_UP, Moves.KNOCK_OFF, Moves.POPULATION_BOMB ], [Species.MINCCINO]: [ Moves.ICICLE_SPEAR, Moves.TIDY_UP, Moves.KNOCK_OFF, Moves.POPULATION_BOMB ],
[Species.GOTHITA]: [ Moves.RECOVER, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.LUMINA_CRASH ], [Species.GOTHITA]: [ Moves.RECOVER, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.LUMINA_CRASH ],
[Species.SOLOSIS]: [ Moves.EXPANDING_FORCE, Moves.TRICK_ROOM, Moves.AURA_SPHERE, Moves.LIGHT_OF_RUIN ], [Species.SOLOSIS]: [ Moves.MIST_BALL, Moves.SPEED_SWAP, Moves.FLAMETHROWER, Moves.LIGHT_OF_RUIN ],
[Species.DUCKLETT]: [ Moves.SPLISHY_SPLASH, Moves.EARTH_POWER, Moves.WILDBOLT_STORM, Moves.QUIVER_DANCE ], [Species.DUCKLETT]: [ Moves.SPLISHY_SPLASH, Moves.SANDSEAR_STORM, Moves.WILDBOLT_STORM, Moves.QUIVER_DANCE ],
[Species.VANILLITE]: [ Moves.EARTH_POWER, Moves.AURORA_VEIL, Moves.CALM_MIND, Moves.SPARKLY_SWIRL ], [Species.VANILLITE]: [ Moves.EARTH_POWER, Moves.AURORA_VEIL, Moves.CALM_MIND, Moves.SPARKLY_SWIRL ],
[Species.DEERLING]: [ Moves.TIDY_UP, Moves.FLOWER_TRICK, Moves.BODY_SLAM, Moves.COMBAT_TORQUE ], [Species.DEERLING]: [ Moves.TIDY_UP, Moves.FLOWER_TRICK, Moves.BODY_SLAM, Moves.COMBAT_TORQUE ],
[Species.EMOLGA]: [ Moves.TRIPLE_AXEL, Moves.SPLISHY_SPLASH, Moves.FLOATY_FALL, Moves.AURA_WHEEL ], [Species.EMOLGA]: [ Moves.ICICLE_CRASH, Moves.ZING_ZAP, Moves.FLOATY_FALL, Moves.ELECTRIFY ],
[Species.KARRABLAST]: [ Moves.LEECH_LIFE, Moves.BITTER_BLADE, Moves.HIGH_HORSEPOWER, Moves.DOUBLE_IRON_BASH ], [Species.KARRABLAST]: [ Moves.LEECH_LIFE, Moves.BITTER_BLADE, Moves.OBSTRUCT, Moves.DOUBLE_IRON_BASH ],
[Species.FOONGUS]: [ Moves.POLLEN_PUFF, Moves.PARTING_SHOT, Moves.FOUL_PLAY, Moves.SAPPY_SEED ], [Species.FOONGUS]: [ Moves.POLLEN_PUFF, Moves.PARTING_SHOT, Moves.FOUL_PLAY, Moves.SAPPY_SEED ],
[Species.FRILLISH]: [ Moves.STRENGTH_SAP, Moves.BUZZY_BUZZ, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ], [Species.FRILLISH]: [ Moves.CALM_MIND, Moves.BUZZY_BUZZ, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ],
[Species.ALOMOMOLA]: [ Moves.FLIP_TURN, Moves.HEART_SWAP, Moves.GLITZY_GLOW, Moves.REVIVAL_BLESSING ], [Species.ALOMOMOLA]: [ Moves.FLIP_TURN, Moves.HEART_SWAP, Moves.GLITZY_GLOW, Moves.REVIVAL_BLESSING ],
[Species.JOLTIK]: [ Moves.WILDBOLT_STORM, Moves.PARABOLIC_CHARGE, Moves.EARTH_POWER, Moves.QUIVER_DANCE ], [Species.JOLTIK]: [ Moves.WILDBOLT_STORM, Moves.PARABOLIC_CHARGE, Moves.EARTH_POWER, Moves.QUIVER_DANCE ],
[Species.FERROSEED]: [ Moves.STRENGTH_SAP, Moves.BODY_PRESS, Moves.SPIKY_SHIELD, Moves.SAPPY_SEED ], [Species.FERROSEED]: [ Moves.SYNTHESIS, Moves.COMBAT_TORQUE, Moves.SPIKY_SHIELD, Moves.SAPPY_SEED ],
[Species.KLINK]: [ Moves.TRIPLE_AXEL, Moves.HIGH_HORSEPOWER, Moves.FUSION_BOLT, Moves.DOUBLE_IRON_BASH ], [Species.KLINK]: [ Moves.TRIPLE_AXEL, Moves.HIGH_HORSEPOWER, Moves.RECOVER, Moves.AURA_WHEEL ],
[Species.TYNAMO]: [ Moves.SCALD, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.AURA_WHEEL ], [Species.TYNAMO]: [ Moves.SCALD, Moves.STRENGTH_SAP, Moves.FIRE_LASH, Moves.AURA_WHEEL ],
[Species.ELGYEM]: [ Moves.LUSTER_PURGE, Moves.BADDY_BAD, Moves.AURA_SPHERE, Moves.TAIL_GLOW ], [Species.ELGYEM]: [ Moves.THUNDERCLAP, Moves.BADDY_BAD, Moves.AURA_SPHERE, Moves.PHOTON_GEYSER ],
[Species.LITWICK]: [ Moves.FIERY_DANCE, Moves.EARTH_POWER, Moves.MOONBLAST, Moves.ASTRAL_BARRAGE ], [Species.LITWICK]: [ Moves.PARTING_SHOT, Moves.EARTH_POWER, Moves.MOONBLAST, Moves.TORCH_SONG ],
[Species.AXEW]: [ Moves.STONE_AXE, Moves.DIRE_CLAW, Moves.BITTER_BLADE, Moves.GLAIVE_RUSH ], [Species.AXEW]: [ Moves.STONE_AXE, Moves.DIRE_CLAW, Moves.BITTER_BLADE, Moves.GLAIVE_RUSH ],
[Species.CUBCHOO]: [ Moves.MOUNTAIN_GALE, Moves.AQUA_STEP, Moves.ICE_SHARD, Moves.COLLISION_COURSE ], [Species.CUBCHOO]: [ Moves.MOUNTAIN_GALE, Moves.AQUA_STEP, Moves.ICE_SHARD, Moves.COLLISION_COURSE ],
[Species.CRYOGONAL]: [ Moves.FREEZING_GLARE, Moves.AURORA_VEIL, Moves.NASTY_PLOT, Moves.ORIGIN_PULSE ], [Species.CRYOGONAL]: [ Moves.FREEZING_GLARE, Moves.AURORA_VEIL, Moves.NASTY_PLOT, Moves.ORIGIN_PULSE ],
[Species.SHELMET]: [ Moves.POWER_GEM, Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.STEAM_ERUPTION ], [Species.SHELMET]: [ Moves.POWER_GEM, Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.STEAM_ERUPTION ],
[Species.STUNFISK]: [ Moves.BANEFUL_BUNKER, Moves.SANDSEAR_STORM, Moves.STRENGTH_SAP, Moves.THUNDERCLAP ], [Species.STUNFISK]: [ Moves.THUNDERCLAP, Moves.SANDSEAR_STORM, Moves.STRENGTH_SAP, Moves.THUNDER_CAGE ],
[Species.MIENFOO]: [ Moves.GUNK_SHOT, Moves.SUPERCELL_SLAM, Moves.KNOCK_OFF, Moves.MOUNTAIN_GALE ], [Species.MIENFOO]: [ Moves.GUNK_SHOT, Moves.SUPERCELL_SLAM, Moves.MOUNTAIN_GALE, Moves.WICKED_BLOW ],
[Species.DRUDDIGON]: [ Moves.FIRE_LASH, Moves.ROOST, Moves.DRAGON_DARTS, Moves.CLANGOROUS_SOUL ], [Species.DRUDDIGON]: [ Moves.FIRE_LASH, Moves.MORNING_SUN, Moves.DRAGON_DARTS, Moves.CLANGOROUS_SOUL ],
[Species.GOLETT]: [ Moves.SHIFT_GEAR, Moves.DRAIN_PUNCH, Moves.HEADLONG_RUSH, Moves.RAGE_FIST ], [Species.GOLETT]: [ Moves.SHIFT_GEAR, Moves.DRAIN_PUNCH, Moves.HEADLONG_RUSH, Moves.RAGE_FIST ],
[Species.PAWNIARD]: [ Moves.SUCKER_PUNCH, Moves.CEASELESS_EDGE, Moves.BITTER_BLADE, Moves.LAST_RESPECTS ], [Species.PAWNIARD]: [ Moves.SUCKER_PUNCH, Moves.CEASELESS_EDGE, Moves.BITTER_BLADE, Moves.LAST_RESPECTS ],
[Species.BOUFFALANT]: [ Moves.SLACK_OFF, Moves.HIGH_JUMP_KICK, Moves.HEAD_SMASH, Moves.FLARE_BLITZ ], [Species.BOUFFALANT]: [ Moves.SLACK_OFF, Moves.HIGH_JUMP_KICK, Moves.HEAD_SMASH, Moves.FLARE_BLITZ ],
@ -321,59 +325,62 @@ export const speciesEggMoves = {
[Species.HEATMOR]: [ Moves.EARTH_POWER, Moves.OVERHEAT, Moves.THUNDERBOLT, Moves.V_CREATE ], [Species.HEATMOR]: [ Moves.EARTH_POWER, Moves.OVERHEAT, Moves.THUNDERBOLT, Moves.V_CREATE ],
[Species.DURANT]: [ Moves.HIGH_HORSEPOWER, Moves.FIRST_IMPRESSION, Moves.SWORDS_DANCE, Moves.BEHEMOTH_BASH ], [Species.DURANT]: [ Moves.HIGH_HORSEPOWER, Moves.FIRST_IMPRESSION, Moves.SWORDS_DANCE, Moves.BEHEMOTH_BASH ],
[Species.DEINO]: [ Moves.FIERY_WRATH, Moves.ESPER_WING, Moves.SLUDGE_BOMB, Moves.FICKLE_BEAM ], [Species.DEINO]: [ Moves.FIERY_WRATH, Moves.ESPER_WING, Moves.SLUDGE_BOMB, Moves.FICKLE_BEAM ],
[Species.LARVESTA]: [ Moves.THUNDERBOLT, Moves.MATCHA_GOTCHA, Moves.EARTH_POWER, Moves.TORCH_SONG ], [Species.LARVESTA]: [ Moves.THUNDERBOLT, Moves.MAGMA_STORM, Moves.EARTH_POWER, Moves.MATCHA_GOTCHA ],
[Species.COBALION]: [ Moves.BEHEMOTH_BLADE, Moves.MIGHTY_CLEAVE, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ], [Species.COBALION]: [ Moves.BEHEMOTH_BLADE, Moves.MIGHTY_CLEAVE, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ],
[Species.TERRAKION]: [ Moves.MIGHTY_CLEAVE, Moves.HEADLONG_RUSH, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ], [Species.TERRAKION]: [ Moves.MIGHTY_CLEAVE, Moves.HEADLONG_RUSH, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ],
[Species.VIRIZION]: [ Moves.PSYBLADE, Moves.SAPPY_SEED, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ], [Species.VIRIZION]: [ Moves.PSYBLADE, Moves.SAPPY_SEED, Moves.CEASELESS_EDGE, Moves.VICTORY_DANCE ],
[Species.TORNADUS]: [ Moves.EARTH_POWER, Moves.PARTING_SHOT, Moves.ICE_BEAM, Moves.OBLIVION_WING ], [Species.TORNADUS]: [ Moves.SANDSEAR_STORM, Moves.PARTING_SHOT, Moves.SPLISHY_SPLASH, Moves.OBLIVION_WING ],
[Species.THUNDURUS]: [ Moves.EARTH_POWER, Moves.HURRICANE, Moves.FROST_BREATH, Moves.ELECTRO_SHOT ], [Species.THUNDURUS]: [ Moves.SANDSEAR_STORM, Moves.HURRICANE, Moves.FROST_BREATH, Moves.ELECTRO_SHOT ],
[Species.RESHIRAM]: [ Moves.ENERGY_BALL, Moves.TAKE_HEART, Moves.FICKLE_BEAM, Moves.ERUPTION ], [Species.RESHIRAM]: [ Moves.ENERGY_BALL, Moves.TAKE_HEART, Moves.FICKLE_BEAM, Moves.ERUPTION ],
[Species.ZEKROM]: [ Moves.TRIPLE_AXEL, Moves.THUNDEROUS_KICK, Moves.DRAGON_HAMMER, Moves.BOLT_BEAK ], [Species.ZEKROM]: [ Moves.TRIPLE_AXEL, Moves.THUNDEROUS_KICK, Moves.DRAGON_HAMMER, Moves.BOLT_BEAK ],
[Species.LANDORUS]: [ Moves.STONE_AXE, Moves.FLOATY_FALL, Moves.ROOST, Moves.BLEAKWIND_STORM ], [Species.LANDORUS]: [ Moves.STONE_AXE, Moves.FLOATY_FALL, Moves.ROOST, Moves.BLEAKWIND_STORM ],
[Species.KYUREM]: [ Moves.DRAGON_DARTS, Moves.GLACIAL_LANCE, Moves.NO_RETREAT, Moves.DRAGON_ENERGY ], [Species.KYUREM]: [ Moves.DRAGON_DARTS, Moves.GLACIAL_LANCE, Moves.NO_RETREAT, Moves.DRAGON_ENERGY ],
[Species.KELDEO]: [ Moves.BOUNCY_BUBBLE, Moves.THUNDERBOLT, Moves.FREEZE_DRY, Moves.STEAM_ERUPTION ], [Species.KELDEO]: [ Moves.BOUNCY_BUBBLE, Moves.THUNDERBOLT, Moves.ICE_BEAM, Moves.STEAM_ERUPTION ],
[Species.MELOETTA]: [ Moves.BODY_SLAM, Moves.TORCH_SONG, Moves.TRIPLE_ARROWS, Moves.BOOMBURST ], [Species.MELOETTA]: [ Moves.BODY_SLAM, Moves.TORCH_SONG, Moves.TRIPLE_ARROWS, Moves.BOOMBURST ],
[Species.GENESECT]: [ Moves.EXTREME_SPEED, Moves.U_TURN, Moves.TACHYON_CUTTER, Moves.TAIL_GLOW ], [Species.GENESECT]: [ Moves.EXTREME_SPEED, Moves.SHIFT_GEAR, Moves.BEHEMOTH_BASH, Moves.TACHYON_CUTTER ],
[Species.CHESPIN]: [ Moves.BODY_PRESS, Moves.SYNTHESIS, Moves.CEASELESS_EDGE, Moves.SAPPY_SEED ],
[Species.FENNEKIN]: [ Moves.EXPANDING_FORCE, Moves.MOONBLAST, Moves.THUNDERBOLT, Moves.TORCH_SONG ], [Species.CHESPIN]: [ Moves.COMBAT_TORQUE, Moves.SYNTHESIS, Moves.CEASELESS_EDGE, Moves.SAPPY_SEED ],
[Species.FENNEKIN]: [ Moves.TWIN_BEAM, Moves.FIERY_DANCE, Moves.THUNDERBOLT, Moves.SPARKLY_SWIRL ],
[Species.FROAKIE]: [ Moves.MOONBLAST, Moves.SHELL_SIDE_ARM, Moves.FIERY_WRATH, Moves.STEAM_ERUPTION ], [Species.FROAKIE]: [ Moves.MOONBLAST, Moves.SHELL_SIDE_ARM, Moves.FIERY_WRATH, Moves.STEAM_ERUPTION ],
[Species.BUNNELBY]: [ Moves.DRAIN_PUNCH, Moves.TIDY_UP, Moves.FACADE, Moves.EXTREME_SPEED ], [Species.BUNNELBY]: [ Moves.DRAIN_PUNCH, Moves.TIDY_UP, Moves.FACADE, Moves.EXTREME_SPEED ],
[Species.FLETCHLING]: [ Moves.DRILL_RUN, Moves.BURNING_BULWARK, Moves.HEAD_SMASH, Moves.VOLT_TACKLE ], [Species.FLETCHLING]: [ Moves.DRILL_RUN, Moves.BURNING_BULWARK, Moves.HEAD_SMASH, Moves.VOLT_TACKLE ],
[Species.SCATTERBUG]: [ Moves.FOCUS_BLAST, Moves.AFTER_YOU, Moves.DECORATE, Moves.BLIZZARD ], [Species.SCATTERBUG]: [ Moves.FOCUS_BLAST, Moves.AFTER_YOU, Moves.DECORATE, Moves.BLIZZARD ],
[Species.LITLEO]: [ Moves.EARTH_POWER, Moves.NASTY_PLOT, Moves.YAWN, Moves.TORCH_SONG ], [Species.LITLEO]: [ Moves.EARTH_POWER, Moves.NASTY_PLOT, Moves.BURNING_BULWARK, Moves.BLUE_FLARE ],
[Species.FLABEBE]: [ Moves.GLITZY_GLOW, Moves.MYSTICAL_FIRE, Moves.TAKE_HEART, Moves.SEED_FLARE ], [Species.FLABEBE]: [ Moves.GLITZY_GLOW, Moves.MYSTICAL_FIRE, Moves.TAKE_HEART, Moves.SEED_FLARE ],
[Species.SKIDDO]: [ Moves.HIGH_HORSEPOWER, Moves.GRASSY_GLIDE, Moves.STONE_AXE, Moves.SAPPY_SEED ], [Species.SKIDDO]: [ Moves.HIGH_HORSEPOWER, Moves.GRASSY_GLIDE, Moves.STONE_AXE, Moves.SAPPY_SEED ],
[Species.PANCHAM]: [ Moves.DRAIN_PUNCH, Moves.SUCKER_PUNCH, Moves.METEOR_MASH, Moves.WICKED_BLOW ], [Species.PANCHAM]: [ Moves.DRAIN_PUNCH, Moves.SUCKER_PUNCH, Moves.METEOR_MASH, Moves.WICKED_BLOW ],
[Species.FURFROU]: [ Moves.TIDY_UP, Moves.SLACK_OFF, Moves.COMBAT_TORQUE, Moves.MULTI_ATTACK ], [Species.FURFROU]: [ Moves.TIDY_UP, Moves.SLACK_OFF, Moves.COMBAT_TORQUE, Moves.MULTI_ATTACK ],
[Species.ESPURR]: [ Moves.LUSTER_PURGE, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.DARK_VOID ], [Species.ESPURR]: [ Moves.LUSTER_PURGE, Moves.MOONBLAST, Moves.AURA_SPHERE, Moves.DARK_VOID ],
[Species.HONEDGE]: [ Moves.TACHYON_CUTTER, Moves.SHADOW_BONE, Moves.BITTER_BLADE, Moves.BEHEMOTH_BLADE ], [Species.HONEDGE]: [ Moves.TACHYON_CUTTER, Moves.SHADOW_BONE, Moves.BITTER_BLADE, Moves.BEHEMOTH_BLADE ],
[Species.SPRITZEE]: [ Moves.SPEED_SWAP, Moves.TORCH_SONG, Moves.ROOST, Moves.REVIVAL_BLESSING ], [Species.SPRITZEE]: [ Moves.SPEED_SWAP, Moves.REVIVAL_BLESSING, Moves.ROOST, Moves.TORCH_SONG ],
[Species.SWIRLIX]: [ Moves.BELLY_DRUM, Moves.HEADLONG_RUSH, Moves.MAGICAL_TORQUE, Moves.REVIVAL_BLESSING ], [Species.SWIRLIX]: [ Moves.BELLY_DRUM, Moves.HEADLONG_RUSH, Moves.MAGICAL_TORQUE, Moves.REVIVAL_BLESSING ],
[Species.INKAY]: [ Moves.POWER_TRIP, Moves.SPIN_OUT, Moves.RECOVER, Moves.PSYCHO_BOOST ], [Species.INKAY]: [ Moves.POWER_TRIP, Moves.SPIN_OUT, Moves.RECOVER, Moves.PSYCHO_BOOST ],
[Species.BINACLE]: [ Moves.TRIPLE_AXEL, Moves.CRABHAMMER, Moves.DIRE_CLAW, Moves.MIGHTY_CLEAVE ], [Species.BINACLE]: [ Moves.TRIPLE_AXEL, Moves.CRABHAMMER, Moves.DIRE_CLAW, Moves.MIGHTY_CLEAVE ],
[Species.SKRELP]: [ Moves.STRENGTH_SAP, Moves.TRICK_ROOM, Moves.CALM_MIND, Moves.CORE_ENFORCER ], [Species.SKRELP]: [ Moves.STRENGTH_SAP, Moves.TRICK_ROOM, Moves.CALM_MIND, Moves.CORE_ENFORCER ],
[Species.CLAUNCHER]: [ Moves.SHELL_SMASH, Moves.ARMOR_CANNON, Moves.WATER_SHURIKEN, Moves.ORIGIN_PULSE ], [Species.CLAUNCHER]: [ Moves.SHELL_SMASH, Moves.ARMOR_CANNON, Moves.ENERGY_BALL, Moves.ORIGIN_PULSE ],
[Species.HELIOPTILE]: [ Moves.WEATHER_BALL, Moves.HYDRO_STEAM, Moves.EARTH_POWER, Moves.BOOMBURST ], [Species.HELIOPTILE]: [ Moves.WEATHER_BALL, Moves.HYDRO_STEAM, Moves.EARTH_POWER, Moves.BOOMBURST ],
[Species.TYRUNT]: [ Moves.DRAGON_HAMMER, Moves.FLARE_BLITZ, Moves.VOLT_TACKLE, Moves.SHIFT_GEAR ], [Species.TYRUNT]: [ Moves.DRAGON_HAMMER, Moves.FLARE_BLITZ, Moves.VOLT_TACKLE, Moves.SHIFT_GEAR ],
[Species.AMAURA]: [ Moves.RECOVER, Moves.AURORA_VEIL, Moves.POWER_GEM, Moves.GEOMANCY ], [Species.AMAURA]: [ Moves.RECOVER, Moves.WRING_OUT, Moves.POWER_GEM, Moves.GEOMANCY ],
[Species.HAWLUCHA]: [ Moves.TRIPLE_AXEL, Moves.HIGH_HORSEPOWER, Moves.FLOATY_FALL, Moves.WICKED_BLOW ], [Species.HAWLUCHA]: [ Moves.TRIPLE_AXEL, Moves.HIGH_HORSEPOWER, Moves.FLOATY_FALL, Moves.WICKED_BLOW ],
[Species.DEDENNE]: [ Moves.BOOMBURST, Moves.FAKE_OUT, Moves.NASTY_PLOT, Moves.REVIVAL_BLESSING ], [Species.DEDENNE]: [ Moves.BOOMBURST, Moves.FAKE_OUT, Moves.NASTY_PLOT, Moves.REVIVAL_BLESSING ],
[Species.CARBINK]: [ Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SPARKLY_SWIRL, Moves.DIAMOND_STORM ], [Species.CARBINK]: [ Moves.BODY_PRESS, Moves.SHORE_UP, Moves.SPARKLY_SWIRL, Moves.DIAMOND_STORM ],
[Species.GOOMY]: [ Moves.SCALD, Moves.RECOVER, Moves.CALM_MIND, Moves.MAKE_IT_RAIN ], [Species.GOOMY]: [ Moves.DRAGON_HAMMER, Moves.RECOVER, Moves.CALM_MIND, Moves.MAKE_IT_RAIN ],
[Species.KLEFKI]: [ Moves.HEAL_BELL, Moves.ENCORE, Moves.INSTRUCT, Moves.TOPSY_TURVY ], [Species.KLEFKI]: [ Moves.HEAL_BELL, Moves.ENCORE, Moves.INSTRUCT, Moves.TOPSY_TURVY ],
[Species.PHANTUMP]: [ Moves.RAGE_FIST, Moves.TRICK_ROOM, Moves.SYNTHESIS, Moves.SAPPY_SEED ], [Species.PHANTUMP]: [ Moves.RAGE_FIST, Moves.SLEEP_POWDER, Moves.SYNTHESIS, Moves.SAPPY_SEED ],
[Species.PUMPKABOO]: [ Moves.SPIRIT_SHACKLE, Moves.FIRE_LASH, Moves.DIRE_CLAW, Moves.SAPPY_SEED ], [Species.PUMPKABOO]: [ Moves.SPIRIT_SHACKLE, Moves.FIRE_LASH, Moves.DIRE_CLAW, Moves.SAPPY_SEED ],
[Species.BERGMITE]: [ Moves.STONE_AXE, Moves.METAL_BURST, Moves.BODY_PRESS, Moves.GLACIAL_LANCE ], [Species.BERGMITE]: [ Moves.STONE_AXE, Moves.METAL_BURST, Moves.BODY_PRESS, Moves.GLACIAL_LANCE ],
[Species.NOIBAT]: [ Moves.AEROBLAST, Moves.OVERDRIVE, Moves.NASTY_PLOT, Moves.CLANGING_SCALES ], [Species.NOIBAT]: [ Moves.AEROBLAST, Moves.OVERDRIVE, Moves.NASTY_PLOT, Moves.CLANGING_SCALES ],
[Species.XERNEAS]: [ Moves.EARTH_POWER, Moves.SPRINGTIDE_STORM, Moves.STRENGTH_SAP, Moves.TAIL_GLOW ], [Species.XERNEAS]: [ Moves.EARTH_POWER, Moves.SPRINGTIDE_STORM, Moves.STRENGTH_SAP, Moves.TAIL_GLOW ],
[Species.YVELTAL]: [ Moves.SHELL_SIDE_ARM, Moves.POWER_TRIP, Moves.FIERY_WRATH, Moves.CLANGOROUS_SOUL ], [Species.YVELTAL]: [ Moves.SHELL_SIDE_ARM, Moves.POWER_TRIP, Moves.FIERY_WRATH, Moves.CLANGOROUS_SOUL ],
[Species.ZYGARDE]: [ Moves.DRAGON_DARTS, Moves.HEAL_ORDER, Moves.CLANGOROUS_SOUL, Moves.DOUBLE_IRON_BASH ], [Species.ZYGARDE]: [ Moves.DRAGON_DARTS, Moves.HEAL_ORDER, Moves.CLANGOROUS_SOUL, Moves.DOUBLE_IRON_BASH ],
[Species.DIANCIE]: [ Moves.MAGICAL_TORQUE, Moves.AURA_SPHERE, Moves.SHORE_UP, Moves.GEOMANCY ], [Species.DIANCIE]: [ Moves.MAGICAL_TORQUE, Moves.FIERY_DANCE, Moves.SHORE_UP, Moves.GEOMANCY ],
[Species.HOOPA]: [ Moves.PHOTON_GEYSER, Moves.SECRET_SWORD, Moves.FIERY_WRATH, Moves.SHELL_SMASH ], [Species.HOOPA]: [ Moves.PHOTON_GEYSER, Moves.SECRET_SWORD, Moves.FIERY_WRATH, Moves.SHELL_SMASH ],
[Species.VOLCANION]: [ Moves.HYDRO_STEAM, Moves.CALM_MIND, Moves.ENERGY_BALL, Moves.MAGMA_STORM ], [Species.VOLCANION]: [ Moves.HYDRO_STEAM, Moves.CALM_MIND, Moves.ENERGY_BALL, Moves.MAGMA_STORM ],
[Species.ETERNAL_FLOETTE]: [ Moves.MIND_BLOWN, Moves.CHLOROBLAST, Moves.LUSTER_PURGE, Moves.QUIVER_DANCE ],
[Species.ROWLET]: [ Moves.THOUSAND_ARROWS, Moves.SHADOW_BONE, Moves.FIRST_IMPRESSION, Moves.VICTORY_DANCE ], [Species.ROWLET]: [ Moves.THOUSAND_ARROWS, Moves.SHADOW_BONE, Moves.FIRST_IMPRESSION, Moves.VICTORY_DANCE ],
[Species.LITTEN]: [ Moves.FAKE_OUT, Moves.PARTING_SHOT, Moves.MORNING_SUN, Moves.SACRED_FIRE ], [Species.LITTEN]: [ Moves.SUCKER_PUNCH, Moves.PARTING_SHOT, Moves.SLACK_OFF, Moves.SACRED_FIRE ],
[Species.POPPLIO]: [ Moves.PSYCHIC_NOISE, Moves.BOUNCY_BUBBLE, Moves.ALLURING_VOICE, Moves.TORCH_SONG ], [Species.POPPLIO]: [ Moves.PSYCHIC_NOISE, Moves.BOUNCY_BUBBLE, Moves.OVERDRIVE, Moves.TORCH_SONG ],
[Species.PIKIPEK]: [ Moves.DUAL_WINGBEAT, Moves.BONE_RUSH, Moves.BURNING_BULWARK, Moves.POPULATION_BOMB ], [Species.PIKIPEK]: [ Moves.DUAL_WINGBEAT, Moves.BONE_RUSH, Moves.BURNING_BULWARK, Moves.POPULATION_BOMB ],
[Species.YUNGOOS]: [ Moves.EXTREME_SPEED, Moves.KNOCK_OFF, Moves.TIDY_UP, Moves.MULTI_ATTACK ], [Species.YUNGOOS]: [ Moves.EXTREME_SPEED, Moves.KNOCK_OFF, Moves.TIDY_UP, Moves.MULTI_ATTACK ],
[Species.GRUBBIN]: [ Moves.ICE_BEAM, Moves.EARTH_POWER, Moves.THUNDERCLAP, Moves.QUIVER_DANCE ], [Species.GRUBBIN]: [ Moves.ICE_BEAM, Moves.EARTH_POWER, Moves.THUNDERCLAP, Moves.QUIVER_DANCE ],
@ -381,7 +388,7 @@ export const speciesEggMoves = {
[Species.ORICORIO]: [ Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.THUNDERCLAP, Moves.OBLIVION_WING ], [Species.ORICORIO]: [ Moves.QUIVER_DANCE, Moves.FIERY_DANCE, Moves.THUNDERCLAP, Moves.OBLIVION_WING ],
[Species.CUTIEFLY]: [ Moves.STICKY_WEB, Moves.SLEEP_POWDER, Moves.HEAT_WAVE, Moves.SPARKLY_SWIRL ], [Species.CUTIEFLY]: [ Moves.STICKY_WEB, Moves.SLEEP_POWDER, Moves.HEAT_WAVE, Moves.SPARKLY_SWIRL ],
[Species.ROCKRUFF]: [ Moves.HIGH_HORSEPOWER, Moves.TIDY_UP, Moves.ICE_SPINNER, Moves.MIGHTY_CLEAVE ], [Species.ROCKRUFF]: [ Moves.HIGH_HORSEPOWER, Moves.TIDY_UP, Moves.ICE_SPINNER, Moves.MIGHTY_CLEAVE ],
[Species.WISHIWASHI]: [ Moves.HEAL_ORDER, Moves.ICE_SPINNER, Moves.DRAGON_DANCE, Moves.JET_PUNCH ], [Species.WISHIWASHI]: [ Moves.HEAL_ORDER, Moves.FREEZE_DRY, Moves.WATER_SHURIKEN, Moves.TAIL_GLOW ],
[Species.MAREANIE]: [ Moves.CEASELESS_EDGE, Moves.SIZZLY_SLIDE, Moves.BODY_PRESS, Moves.LEECH_SEED ], [Species.MAREANIE]: [ Moves.CEASELESS_EDGE, Moves.SIZZLY_SLIDE, Moves.BODY_PRESS, Moves.LEECH_SEED ],
[Species.MUDBRAY]: [ Moves.BODY_PRESS, Moves.YAWN, Moves.SHORE_UP, Moves.THOUSAND_WAVES ], [Species.MUDBRAY]: [ Moves.BODY_PRESS, Moves.YAWN, Moves.SHORE_UP, Moves.THOUSAND_WAVES ],
[Species.DEWPIDER]: [ Moves.JET_PUNCH, Moves.SILK_TRAP, Moves.SWORDS_DANCE, Moves.AQUA_STEP ], [Species.DEWPIDER]: [ Moves.JET_PUNCH, Moves.SILK_TRAP, Moves.SWORDS_DANCE, Moves.AQUA_STEP ],
@ -392,27 +399,27 @@ export const speciesEggMoves = {
[Species.BOUNSWEET]: [ Moves.TRIPLE_AXEL, Moves.AQUA_STEP, Moves.THUNDEROUS_KICK, Moves.SAPPY_SEED ], [Species.BOUNSWEET]: [ Moves.TRIPLE_AXEL, Moves.AQUA_STEP, Moves.THUNDEROUS_KICK, Moves.SAPPY_SEED ],
[Species.COMFEY]: [ Moves.REVIVAL_BLESSING, Moves.TAKE_HEART, Moves.STRENGTH_SAP, Moves.MATCHA_GOTCHA ], [Species.COMFEY]: [ Moves.REVIVAL_BLESSING, Moves.TAKE_HEART, Moves.STRENGTH_SAP, Moves.MATCHA_GOTCHA ],
[Species.ORANGURU]: [ Moves.JUNGLE_HEALING, Moves.YAWN, Moves.FOLLOW_ME, Moves.LUMINA_CRASH ], [Species.ORANGURU]: [ Moves.JUNGLE_HEALING, Moves.YAWN, Moves.FOLLOW_ME, Moves.LUMINA_CRASH ],
[Species.PASSIMIAN]: [ Moves.FAKE_OUT, Moves.SUCKER_PUNCH, Moves.ZING_ZAP, Moves.PYRO_BALL ], [Species.PASSIMIAN]: [ Moves.PYRO_BALL, Moves.SUCKER_PUNCH, Moves.ZING_ZAP, Moves.VICTORY_DANCE ],
[Species.WIMPOD]: [ Moves.TRIPLE_AXEL, Moves.OBSTRUCT, Moves.JET_PUNCH, Moves.SURGING_STRIKES ], [Species.WIMPOD]: [ Moves.TRIPLE_AXEL, Moves.OBSTRUCT, Moves.JET_PUNCH, Moves.SURGING_STRIKES ],
[Species.SANDYGAST]: [ Moves.SANDSEAR_STORM, Moves.SPLISHY_SPLASH, Moves.TAKE_HEART, Moves.SALT_CURE ], [Species.SANDYGAST]: [ Moves.BITTER_MALICE, Moves.SPLISHY_SPLASH, Moves.TAKE_HEART, Moves.SALT_CURE ],
[Species.PYUKUMUKU]: [ Moves.COMEUPPANCE, Moves.BANEFUL_BUNKER, Moves.TOXIC_SPIKES, Moves.SALT_CURE ], [Species.PYUKUMUKU]: [ Moves.COMEUPPANCE, Moves.BANEFUL_BUNKER, Moves.TOXIC_SPIKES, Moves.SALT_CURE ],
[Species.TYPE_NULL]: [ Moves.DIRE_CLAW, Moves.RECOVER, Moves.EXTREME_SPEED, Moves.SHELL_SMASH ], [Species.TYPE_NULL]: [ Moves.DIRE_CLAW, Moves.RECOVER, Moves.COMBAT_TORQUE, Moves.NO_RETREAT ],
[Species.MINIOR]: [ Moves.EARTH_POWER, Moves.FLOATY_FALL, Moves.ZING_ZAP, Moves.DIAMOND_STORM ], [Species.MINIOR]: [ Moves.EARTH_POWER, Moves.FLOATY_FALL, Moves.ZING_ZAP, Moves.DIAMOND_STORM ],
[Species.KOMALA]: [ Moves.SLACK_OFF, Moves.EXTREME_SPEED, Moves.KNOCK_OFF, Moves.COLLISION_COURSE ], [Species.KOMALA]: [ Moves.SLACK_OFF, Moves.EXTREME_SPEED, Moves.KNOCK_OFF, Moves.COLLISION_COURSE ],
[Species.TURTONATOR]: [ Moves.BURNING_BULWARK, Moves.MORNING_SUN, Moves.BODY_PRESS, Moves.CORE_ENFORCER ], [Species.TURTONATOR]: [ Moves.BURNING_BULWARK, Moves.MORNING_SUN, Moves.BODY_PRESS, Moves.CORE_ENFORCER ],
[Species.TOGEDEMARU]: [ Moves.FAKE_OUT, Moves.METAL_BURST, Moves.METEOR_MASH, Moves.AURA_WHEEL ], [Species.TOGEDEMARU]: [ Moves.FAKE_OUT, Moves.METAL_BURST, Moves.METEOR_MASH, Moves.AURA_WHEEL ],
[Species.MIMIKYU]: [ Moves.SPIRIT_BREAK, Moves.TIDY_UP, Moves.BITTER_BLADE, Moves.SPECTRAL_THIEF ], [Species.MIMIKYU]: [ Moves.SPIRIT_BREAK, Moves.TIDY_UP, Moves.FIRE_LASH, Moves.SPECTRAL_THIEF ],
[Species.BRUXISH]: [ Moves.PLAY_ROUGH, Moves.FIRE_FANG, Moves.DRAGON_DANCE, Moves.SURGING_STRIKES ], [Species.BRUXISH]: [ Moves.PLAY_ROUGH, Moves.FIRE_FANG, Moves.DRAGON_DANCE, Moves.SURGING_STRIKES ],
[Species.DRAMPA]: [ Moves.SLACK_OFF, Moves.TRICK_ROOM, Moves.CORE_ENFORCER, Moves.BOOMBURST ], [Species.DRAMPA]: [ Moves.SLACK_OFF, Moves.TRICK_ROOM, Moves.CORE_ENFORCER, Moves.BOOMBURST ],
[Species.DHELMISE]: [ Moves.SHADOW_BONE, Moves.STRENGTH_SAP, Moves.LIQUIDATION, Moves.SAPPY_SEED ], [Species.DHELMISE]: [ Moves.SHADOW_BONE, Moves.IVY_CUDGEL, Moves.TRIPLE_DIVE, Moves.STRENGTH_SAP ],
[Species.JANGMO_O]: [ Moves.BODY_PRESS, Moves.SHELL_SIDE_ARM, Moves.SECRET_SWORD, Moves.GLAIVE_RUSH ], [Species.JANGMO_O]: [ Moves.BODY_PRESS, Moves.SHELL_SIDE_ARM, Moves.SECRET_SWORD, Moves.GLAIVE_RUSH ],
[Species.TAPU_KOKO]: [ Moves.MAGICAL_TORQUE, Moves.TRIPLE_AXEL, Moves.RISING_VOLTAGE, Moves.BOLT_STRIKE ], [Species.TAPU_KOKO]: [ Moves.MAGICAL_TORQUE, Moves.TRIPLE_AXEL, Moves.SWORDS_DANCE, Moves.BOLT_STRIKE ],
[Species.TAPU_LELE]: [ Moves.MOONLIGHT, Moves.NASTY_PLOT, Moves.HEAT_WAVE, Moves.EXPANDING_FORCE ], [Species.TAPU_LELE]: [ Moves.MOONLIGHT, Moves.NASTY_PLOT, Moves.HEAT_WAVE, Moves.EXPANDING_FORCE ],
[Species.TAPU_BULU]: [ Moves.SAPPY_SEED, Moves.DRAIN_PUNCH, Moves.MAGICAL_TORQUE, Moves.VICTORY_DANCE ], [Species.TAPU_BULU]: [ Moves.SAPPY_SEED, Moves.DRAIN_PUNCH, Moves.MAGICAL_TORQUE, Moves.VICTORY_DANCE ],
[Species.TAPU_FINI]: [ Moves.AURA_SPHERE, Moves.EARTH_POWER, Moves.RECOVER, Moves.QUIVER_DANCE ], [Species.TAPU_FINI]: [ Moves.AURA_SPHERE, Moves.EARTH_POWER, Moves.RECOVER, Moves.QUIVER_DANCE ],
[Species.COSMOG]: [ Moves.PHOTON_GEYSER, Moves.PRECIPICE_BLADES, Moves.SACRED_FIRE, Moves.ASTRAL_BARRAGE ], [Species.COSMOG]: [ Moves.PHOTON_GEYSER, Moves.PRECIPICE_BLADES, Moves.SACRED_FIRE, Moves.ASTRAL_BARRAGE ],
[Species.NIHILEGO]: [ Moves.STRENGTH_SAP, Moves.MALIGNANT_CHAIN, Moves.EARTH_POWER, Moves.QUIVER_DANCE ], [Species.NIHILEGO]: [ Moves.STRENGTH_SAP, Moves.MALIGNANT_CHAIN, Moves.EARTH_POWER, Moves.QUIVER_DANCE ],
[Species.BUZZWOLE]: [ Moves.FIRST_IMPRESSION, Moves.COMBAT_TORQUE, Moves.ROCK_WRECKER, Moves.DOUBLE_IRON_BASH ], [Species.BUZZWOLE]: [ Moves.FIRST_IMPRESSION, Moves.COMBAT_TORQUE, Moves.ROCK_BLAST, Moves.DOUBLE_IRON_BASH ],
[Species.PHEROMOSA]: [ Moves.SECRET_SWORD, Moves.MAKE_IT_RAIN, Moves.ATTACK_ORDER, Moves.DIAMOND_STORM ], [Species.PHEROMOSA]: [ Moves.SECRET_SWORD, Moves.MAKE_IT_RAIN, Moves.ATTACK_ORDER, Moves.DIAMOND_STORM ],
[Species.XURKITREE]: [ Moves.FLAMETHROWER, Moves.GIGA_DRAIN, Moves.TAIL_GLOW, Moves.THUNDERCLAP ], [Species.XURKITREE]: [ Moves.FLAMETHROWER, Moves.GIGA_DRAIN, Moves.TAIL_GLOW, Moves.THUNDERCLAP ],
[Species.CELESTEELA]: [ Moves.RECOVER, Moves.BUZZY_BUZZ, Moves.SANDSEAR_STORM, Moves.OBLIVION_WING ], [Species.CELESTEELA]: [ Moves.RECOVER, Moves.BUZZY_BUZZ, Moves.SANDSEAR_STORM, Moves.OBLIVION_WING ],
@ -421,11 +428,19 @@ export const speciesEggMoves = {
[Species.NECROZMA]: [ Moves.DYNAMAX_CANNON, Moves.SACRED_FIRE, Moves.ASTRAL_BARRAGE, Moves.CLANGOROUS_SOUL ], [Species.NECROZMA]: [ Moves.DYNAMAX_CANNON, Moves.SACRED_FIRE, Moves.ASTRAL_BARRAGE, Moves.CLANGOROUS_SOUL ],
[Species.MAGEARNA]: [ Moves.STRENGTH_SAP, Moves.EARTH_POWER, Moves.MOONBLAST, Moves.MAKE_IT_RAIN ], [Species.MAGEARNA]: [ Moves.STRENGTH_SAP, Moves.EARTH_POWER, Moves.MOONBLAST, Moves.MAKE_IT_RAIN ],
[Species.MARSHADOW]: [ Moves.POWER_UP_PUNCH, Moves.TRIPLE_AXEL, Moves.METEOR_MASH, Moves.STORM_THROW ], [Species.MARSHADOW]: [ Moves.POWER_UP_PUNCH, Moves.TRIPLE_AXEL, Moves.METEOR_MASH, Moves.STORM_THROW ],
[Species.POIPOLE]: [ Moves.CORE_ENFORCER, Moves.ICE_BEAM, Moves.SEARING_SHOT, Moves.MALIGNANT_CHAIN ], [Species.POIPOLE]: [ Moves.MALIGNANT_CHAIN, Moves.ICE_BEAM, Moves.ARMOR_CANNON, Moves.CLANGING_SCALES ],
[Species.STAKATAKA]: [ Moves.HEAVY_SLAM, Moves.SHORE_UP, Moves.CURSE, Moves.SALT_CURE ], [Species.STAKATAKA]: [ Moves.HEAVY_SLAM, Moves.SHORE_UP, Moves.CURSE, Moves.SALT_CURE ],
[Species.BLACEPHALON]: [ Moves.NASTY_PLOT, Moves.AURA_SPHERE, Moves.CHLOROBLAST, Moves.ASTRAL_BARRAGE ], [Species.BLACEPHALON]: [ Moves.STEEL_BEAM, Moves.MOONBLAST, Moves.CHLOROBLAST, Moves.MOONGEIST_BEAM ],
[Species.ZERAORA]: [ Moves.SWORDS_DANCE, Moves.TRIPLE_AXEL, Moves.BOLT_STRIKE, Moves.PYRO_BALL ], [Species.ZERAORA]: [ Moves.SWORDS_DANCE, Moves.TRIPLE_AXEL, Moves.BOLT_STRIKE, Moves.PYRO_BALL ],
[Species.MELTAN]: [ Moves.BULLET_PUNCH, Moves.DRAIN_PUNCH, Moves.BULK_UP, Moves.PLASMA_FISTS ], [Species.MELTAN]: [ Moves.BULLET_PUNCH, Moves.DRAIN_PUNCH, Moves.BULK_UP, Moves.PLASMA_FISTS ],
[Species.ALOLA_RATTATA]: [ Moves.FALSE_SURRENDER, Moves.PSYCHIC_FANGS, Moves.COIL, Moves.EXTREME_SPEED ],
[Species.ALOLA_SANDSHREW]: [ Moves.SPIKY_SHIELD, Moves.AQUA_CUTTER, Moves.SHIFT_GEAR, Moves.GLACIAL_LANCE ],
[Species.ALOLA_VULPIX]: [ Moves.MOONBLAST, Moves.PARTING_SHOT, Moves.EARTH_POWER, Moves.REVIVAL_BLESSING ],
[Species.ALOLA_DIGLETT]: [ Moves.THOUSAND_WAVES, Moves.SWORDS_DANCE, Moves.TRIPLE_DIVE, Moves.MOUNTAIN_GALE ],
[Species.ALOLA_MEOWTH]: [ Moves.BADDY_BAD, Moves.BUZZY_BUZZ, Moves.PARTING_SHOT, Moves.MAKE_IT_RAIN ],
[Species.ALOLA_GEODUDE]: [ Moves.THOUSAND_WAVES, Moves.BULK_UP, Moves.STONE_AXE, Moves.EXTREME_SPEED ],
[Species.ALOLA_GRIMER]: [ Moves.SUCKER_PUNCH, Moves.BARB_BARRAGE, Moves.RECOVER, Moves.SURGING_STRIKES ],
[Species.GROOKEY]: [ Moves.HIGH_HORSEPOWER, Moves.CLANGOROUS_SOUL, Moves.GRASSY_GLIDE, Moves.SAPPY_SEED ], [Species.GROOKEY]: [ Moves.HIGH_HORSEPOWER, Moves.CLANGOROUS_SOUL, Moves.GRASSY_GLIDE, Moves.SAPPY_SEED ],
[Species.SCORBUNNY]: [ Moves.EXTREME_SPEED, Moves.HIGH_JUMP_KICK, Moves.TRIPLE_AXEL, Moves.BOLT_STRIKE ], [Species.SCORBUNNY]: [ Moves.EXTREME_SPEED, Moves.HIGH_JUMP_KICK, Moves.TRIPLE_AXEL, Moves.BOLT_STRIKE ],
[Species.SOBBLE]: [ Moves.AEROBLAST, Moves.FROST_BREATH, Moves.ENERGY_BALL, Moves.NASTY_PLOT ], [Species.SOBBLE]: [ Moves.AEROBLAST, Moves.FROST_BREATH, Moves.ENERGY_BALL, Moves.NASTY_PLOT ],
@ -433,15 +448,15 @@ export const speciesEggMoves = {
[Species.ROOKIDEE]: [ Moves.ROOST, Moves.BODY_PRESS, Moves.KINGS_SHIELD, Moves.BEHEMOTH_BASH ], [Species.ROOKIDEE]: [ Moves.ROOST, Moves.BODY_PRESS, Moves.KINGS_SHIELD, Moves.BEHEMOTH_BASH ],
[Species.BLIPBUG]: [ Moves.HEAL_ORDER, Moves.LUSTER_PURGE, Moves.SLEEP_POWDER, Moves.TAIL_GLOW ], [Species.BLIPBUG]: [ Moves.HEAL_ORDER, Moves.LUSTER_PURGE, Moves.SLEEP_POWDER, Moves.TAIL_GLOW ],
[Species.NICKIT]: [ Moves.BADDY_BAD, Moves.FLAMETHROWER, Moves.SPARKLY_SWIRL, Moves.MAKE_IT_RAIN ], [Species.NICKIT]: [ Moves.BADDY_BAD, Moves.FLAMETHROWER, Moves.SPARKLY_SWIRL, Moves.MAKE_IT_RAIN ],
[Species.GOSSIFLEUR]: [ Moves.TAILWIND, Moves.STRENGTH_SAP, Moves.SAPPY_SEED, Moves.SEED_FLARE ], [Species.GOSSIFLEUR]: [ Moves.PARTING_SHOT, Moves.STRENGTH_SAP, Moves.SAPPY_SEED, Moves.SEED_FLARE ],
[Species.WOOLOO]: [ Moves.PSYSHIELD_BASH, Moves.MILK_DRINK, Moves.BODY_PRESS, Moves.MULTI_ATTACK ], [Species.WOOLOO]: [ Moves.PSYSHIELD_BASH, Moves.MILK_DRINK, Moves.BODY_PRESS, Moves.MULTI_ATTACK ],
[Species.CHEWTLE]: [ Moves.ICE_FANG, Moves.ACCELEROCK, Moves.SHELL_SMASH, Moves.FISHIOUS_REND ], [Species.CHEWTLE]: [ Moves.ICE_FANG, Moves.PSYCHIC_FANGS, Moves.SHELL_SMASH, Moves.MIGHTY_CLEAVE ],
[Species.YAMPER]: [ Moves.ICE_FANG, Moves.SWORDS_DANCE, Moves.THUNDER_FANG, Moves.BOLT_STRIKE ], [Species.YAMPER]: [ Moves.ICE_FANG, Moves.SWORDS_DANCE, Moves.THUNDER_FANG, Moves.BOLT_STRIKE ],
[Species.ROLYCOLY]: [ Moves.BITTER_BLADE, Moves.BODY_PRESS, Moves.BULK_UP, Moves.DIAMOND_STORM ], [Species.ROLYCOLY]: [ Moves.BITTER_BLADE, Moves.BODY_PRESS, Moves.BULK_UP, Moves.DIAMOND_STORM ],
[Species.APPLIN]: [ Moves.MATCHA_GOTCHA, Moves.DRAGON_HAMMER, Moves.FLOWER_TRICK, Moves.STRENGTH_SAP ], [Species.APPLIN]: [ Moves.CORE_ENFORCER, Moves.DRAGON_HAMMER, Moves.FLOWER_TRICK, Moves.MATCHA_GOTCHA ],
[Species.SILICOBRA]: [ Moves.SHORE_UP, Moves.SHED_TAIL, Moves.MOUNTAIN_GALE, Moves.THOUSAND_ARROWS ], [Species.SILICOBRA]: [ Moves.SHORE_UP, Moves.SHED_TAIL, Moves.MOUNTAIN_GALE, Moves.THOUSAND_ARROWS ],
[Species.CRAMORANT]: [ Moves.APPLE_ACID, Moves.SURF, Moves.SCORCHING_SANDS, Moves.OBLIVION_WING ], [Species.CRAMORANT]: [ Moves.APPLE_ACID, Moves.SURF, Moves.SCORCHING_SANDS, Moves.OBLIVION_WING ],
[Species.ARROKUDA]: [ Moves.SUPERCELL_SLAM, Moves.KNOCK_OFF, Moves.ICE_SPINNER, Moves.FILLET_AWAY ], [Species.ARROKUDA]: [ Moves.SUPERCELL_SLAM, Moves.TRIPLE_DIVE, Moves.ICE_SPINNER, Moves.SWORDS_DANCE ],
[Species.TOXEL]: [ Moves.NASTY_PLOT, Moves.BUG_BUZZ, Moves.SPARKLING_ARIA, Moves.TORCH_SONG ], [Species.TOXEL]: [ Moves.NASTY_PLOT, Moves.BUG_BUZZ, Moves.SPARKLING_ARIA, Moves.TORCH_SONG ],
[Species.SIZZLIPEDE]: [ Moves.BURNING_BULWARK, Moves.ZING_ZAP, Moves.FIRST_IMPRESSION, Moves.BITTER_BLADE ], [Species.SIZZLIPEDE]: [ Moves.BURNING_BULWARK, Moves.ZING_ZAP, Moves.FIRST_IMPRESSION, Moves.BITTER_BLADE ],
[Species.CLOBBOPUS]: [ Moves.STORM_THROW, Moves.JET_PUNCH, Moves.MACH_PUNCH, Moves.SURGING_STRIKES ], [Species.CLOBBOPUS]: [ Moves.STORM_THROW, Moves.JET_PUNCH, Moves.MACH_PUNCH, Moves.SURGING_STRIKES ],
@ -450,19 +465,19 @@ export const speciesEggMoves = {
[Species.IMPIDIMP]: [ Moves.ENCORE, Moves.PARTING_SHOT, Moves.TOPSY_TURVY, Moves.WICKED_BLOW ], [Species.IMPIDIMP]: [ Moves.ENCORE, Moves.PARTING_SHOT, Moves.TOPSY_TURVY, Moves.WICKED_BLOW ],
[Species.MILCERY]: [ Moves.MOONBLAST, Moves.CHILLY_RECEPTION, Moves.EARTH_POWER, Moves.GEOMANCY ], [Species.MILCERY]: [ Moves.MOONBLAST, Moves.CHILLY_RECEPTION, Moves.EARTH_POWER, Moves.GEOMANCY ],
[Species.FALINKS]: [ Moves.COMBAT_TORQUE, Moves.PSYSHIELD_BASH, Moves.HEAL_ORDER, Moves.POPULATION_BOMB ], [Species.FALINKS]: [ Moves.COMBAT_TORQUE, Moves.PSYSHIELD_BASH, Moves.HEAL_ORDER, Moves.POPULATION_BOMB ],
[Species.PINCURCHIN]: [ Moves.TRICK_ROOM, Moves.RISING_VOLTAGE, Moves.STRENGTH_SAP, Moves.THUNDERCLAP ], [Species.PINCURCHIN]: [ Moves.TRICK_ROOM, Moves.VOLT_SWITCH, Moves.STRENGTH_SAP, Moves.THUNDERCLAP ],
[Species.SNOM]: [ Moves.FROST_BREATH, Moves.HEAL_ORDER, Moves.EARTH_POWER, Moves.SPORE ], [Species.SNOM]: [ Moves.FROST_BREATH, Moves.HEAL_ORDER, Moves.EARTH_POWER, Moves.SPORE ],
[Species.STONJOURNER]: [ Moves.BODY_PRESS, Moves.HELPING_HAND, Moves.ACCELEROCK, Moves.DIAMOND_STORM ], [Species.STONJOURNER]: [ Moves.BODY_PRESS, Moves.HELPING_HAND, Moves.ACCELEROCK, Moves.DIAMOND_STORM ],
[Species.EISCUE]: [ Moves.TRIPLE_AXEL, Moves.AQUA_STEP, Moves.SHELL_SMASH, Moves.GLACIAL_LANCE ], [Species.EISCUE]: [ Moves.TRIPLE_AXEL, Moves.AQUA_STEP, Moves.AXE_KICK, Moves.SHELL_SMASH ],
[Species.INDEEDEE]: [ Moves.MATCHA_GOTCHA, Moves.EXPANDING_FORCE, Moves.MOONBLAST, Moves.REVIVAL_BLESSING ], [Species.INDEEDEE]: [ Moves.MATCHA_GOTCHA, Moves.EXPANDING_FORCE, Moves.MOONBLAST, Moves.REVIVAL_BLESSING ],
[Species.MORPEKO]: [ Moves.TRIPLE_AXEL, Moves.OBSTRUCT, Moves.SWORDS_DANCE, Moves.COLLISION_COURSE ], [Species.MORPEKO]: [ Moves.TRIPLE_AXEL, Moves.OBSTRUCT, Moves.SWORDS_DANCE, Moves.COLLISION_COURSE ],
[Species.CUFANT]: [ Moves.LIQUIDATION, Moves.CURSE, Moves.COMBAT_TORQUE, Moves.GIGATON_HAMMER ], [Species.CUFANT]: [ Moves.LIQUIDATION, Moves.CURSE, Moves.COMBAT_TORQUE, Moves.GIGATON_HAMMER ],
[Species.DRACOZOLT]: [ Moves.TRIPLE_AXEL, Moves.SCALE_SHOT, Moves.FIRE_LASH, Moves.DRAGON_DANCE ], [Species.DRACOZOLT]: [ Moves.TRIPLE_AXEL, Moves.GUNK_SHOT, Moves.FIRE_LASH, Moves.DRAGON_DANCE ],
[Species.ARCTOZOLT]: [ Moves.MOUNTAIN_GALE, Moves.AQUA_STEP, Moves.HIGH_HORSEPOWER, Moves.SHIFT_GEAR ], [Species.ARCTOZOLT]: [ Moves.MOUNTAIN_GALE, Moves.AQUA_STEP, Moves.HIGH_HORSEPOWER, Moves.SHIFT_GEAR ],
[Species.DRACOVISH]: [ Moves.TRIPLE_AXEL, Moves.DRAGON_HAMMER, Moves.THUNDER_FANG, Moves.DRAGON_DANCE ], [Species.DRACOVISH]: [ Moves.TRIPLE_AXEL, Moves.DRAGON_HAMMER, Moves.THUNDER_FANG, Moves.DRAGON_DANCE ],
[Species.ARCTOVISH]: [ Moves.ICE_FANG, Moves.THUNDER_FANG, Moves.HIGH_HORSEPOWER, Moves.SHIFT_GEAR ], [Species.ARCTOVISH]: [ Moves.ICE_FANG, Moves.THUNDER_FANG, Moves.HIGH_HORSEPOWER, Moves.SHIFT_GEAR ],
[Species.DURALUDON]: [ Moves.CORE_ENFORCER, Moves.BODY_PRESS, Moves.RECOVER, Moves.TACHYON_CUTTER ], [Species.DURALUDON]: [ Moves.CORE_ENFORCER, Moves.BODY_PRESS, Moves.RECOVER, Moves.TACHYON_CUTTER ],
[Species.DREEPY]: [ Moves.SHADOW_BONE, Moves.NASTY_PLOT, Moves.FIRE_LASH, Moves.COLLISION_COURSE ], [Species.DREEPY]: [ Moves.SHADOW_BONE, Moves.POWER_UP_PUNCH, Moves.FIRE_LASH, Moves.DIRE_CLAW ],
[Species.ZACIAN]: [ Moves.MAGICAL_TORQUE, Moves.MIGHTY_CLEAVE, Moves.BITTER_BLADE, Moves.PRECIPICE_BLADES ], [Species.ZACIAN]: [ Moves.MAGICAL_TORQUE, Moves.MIGHTY_CLEAVE, Moves.BITTER_BLADE, Moves.PRECIPICE_BLADES ],
[Species.ZAMAZENTA]: [ Moves.BULK_UP, Moves.BODY_PRESS, Moves.SLACK_OFF, Moves.DIAMOND_STORM ], [Species.ZAMAZENTA]: [ Moves.BULK_UP, Moves.BODY_PRESS, Moves.SLACK_OFF, Moves.DIAMOND_STORM ],
[Species.ETERNATUS]: [ Moves.BODY_PRESS, Moves.NASTY_PLOT, Moves.MALIGNANT_CHAIN, Moves.DRAGON_ENERGY ], [Species.ETERNATUS]: [ Moves.BODY_PRESS, Moves.NASTY_PLOT, Moves.MALIGNANT_CHAIN, Moves.DRAGON_ENERGY ],
@ -470,18 +485,36 @@ export const speciesEggMoves = {
[Species.ZARUDE]: [ Moves.SAPPY_SEED, Moves.MIGHTY_CLEAVE, Moves.WICKED_BLOW, Moves.VICTORY_DANCE ], [Species.ZARUDE]: [ Moves.SAPPY_SEED, Moves.MIGHTY_CLEAVE, Moves.WICKED_BLOW, Moves.VICTORY_DANCE ],
[Species.REGIELEKI]: [ Moves.NASTY_PLOT, Moves.ICE_BEAM, Moves.EARTH_POWER, Moves.ELECTRO_DRIFT ], [Species.REGIELEKI]: [ Moves.NASTY_PLOT, Moves.ICE_BEAM, Moves.EARTH_POWER, Moves.ELECTRO_DRIFT ],
[Species.REGIDRAGO]: [ Moves.METEOR_MASH, Moves.FLAMETHROWER, Moves.TAKE_HEART, Moves.DRAGON_DARTS ], [Species.REGIDRAGO]: [ Moves.METEOR_MASH, Moves.FLAMETHROWER, Moves.TAKE_HEART, Moves.DRAGON_DARTS ],
[Species.GLASTRIER]: [ Moves.TRICK_ROOM, Moves.SLACK_OFF, Moves.HIGH_HORSEPOWER, Moves.GLACIAL_LANCE ], [Species.GLASTRIER]: [ Moves.SPEED_SWAP, Moves.SLACK_OFF, Moves.HIGH_HORSEPOWER, Moves.GLACIAL_LANCE ],
[Species.SPECTRIER]: [ Moves.EARTH_POWER, Moves.PARTING_SHOT, Moves.AURA_SPHERE, Moves.ASTRAL_BARRAGE ], [Species.SPECTRIER]: [ Moves.EARTH_POWER, Moves.PARTING_SHOT, Moves.AURA_SPHERE, Moves.ASTRAL_BARRAGE ],
[Species.CALYREX]: [ Moves.SAPPY_SEED, Moves.RECOVER, Moves.SECRET_SWORD, Moves.PHOTON_GEYSER ], [Species.CALYREX]: [ Moves.SAPPY_SEED, Moves.RECOVER, Moves.SECRET_SWORD, Moves.PHOTON_GEYSER ],
[Species.ENAMORUS]: [ Moves.FLEUR_CANNON, Moves.TAKE_HEART, Moves.STORED_POWER, Moves.OBLIVION_WING ], [Species.ENAMORUS]: [ Moves.AEROBLAST, Moves.THOUSAND_ARROWS, Moves.STORED_POWER, Moves.FLEUR_CANNON ],
[Species.GALAR_MEOWTH]: [ Moves.LIQUIDATION, Moves.HORN_LEECH, Moves.BULLET_PUNCH, Moves.BEHEMOTH_BASH ],
[Species.GALAR_PONYTA]: [ Moves.MAGICAL_TORQUE, Moves.EXTREME_SPEED, Moves.FLARE_BLITZ, Moves.PHOTON_GEYSER ],
[Species.GALAR_SLOWPOKE]: [ Moves.SHED_TAIL, Moves.BADDY_BAD, Moves.MOONBLAST, Moves.PHOTON_GEYSER ],
[Species.GALAR_FARFETCHD]: [ Moves.ROOST, Moves.SACRED_SWORD, Moves.KINGS_SHIELD, Moves.BEHEMOTH_BLADE ],
[Species.GALAR_ARTICUNO]: [ Moves.SECRET_SWORD, Moves.NIGHT_DAZE, Moves.ICE_BEAM, Moves.OBLIVION_WING ],
[Species.GALAR_ZAPDOS]: [ Moves.TIDY_UP, Moves.FLOATY_FALL, Moves.ROOST, Moves.BOLT_BEAK ],
[Species.GALAR_MOLTRES]: [ Moves.ROOST, Moves.SLUDGE_BOMB, Moves.FLAMETHROWER, Moves.OBLIVION_WING ],
[Species.GALAR_CORSOLA]: [ Moves.SHELL_SMASH, Moves.AURA_SPHERE, Moves.INFERNAL_PARADE, Moves.ASTRAL_BARRAGE ],
[Species.GALAR_ZIGZAGOON]: [ Moves.CEASELESS_EDGE, Moves.FACADE, Moves.PARTING_SHOT, Moves.EXTREME_SPEED ],
[Species.GALAR_DARUMAKA]: [ Moves.ICE_SPINNER, Moves.ZING_ZAP, Moves.DRAIN_PUNCH, Moves.PYRO_BALL ],
[Species.GALAR_YAMASK]: [ Moves.STRENGTH_SAP, Moves.DIRE_CLAW, Moves.THOUSAND_WAVES, Moves.SPECTRAL_THIEF ],
[Species.GALAR_STUNFISK]: [ Moves.SPIKY_SHIELD, Moves.THOUSAND_ARROWS, Moves.STRENGTH_SAP, Moves.DOUBLE_IRON_BASH ],
[Species.HISUI_GROWLITHE]: [ Moves.WAVE_CRASH, Moves.HEAD_SMASH, Moves.VOLT_TACKLE, Moves.DRAGON_DANCE ],
[Species.HISUI_VOLTORB]: [ Moves.FROST_BREATH, Moves.NASTY_PLOT, Moves.APPLE_ACID, Moves.ELECTRO_DRIFT ],
[Species.HISUI_QWILFISH]: [ Moves.CEASELESS_EDGE, Moves.KNOCK_OFF, Moves.RECOVER, Moves.FISHIOUS_REND ],
[Species.HISUI_SNEASEL]: [ Moves.DRAIN_PUNCH, Moves.KNOCK_OFF, Moves.PSYCHIC_FANGS, Moves.TRIPLE_AXEL ],
[Species.HISUI_ZORUA]: [ Moves.MOONBLAST, Moves.HYPER_VOICE, Moves.PARTING_SHOT, Moves.BLOOD_MOON ],
[Species.SPRIGATITO]: [ Moves.FIRE_LASH, Moves.TRIPLE_AXEL, Moves.SUCKER_PUNCH, Moves.WICKED_BLOW ], [Species.SPRIGATITO]: [ Moves.FIRE_LASH, Moves.TRIPLE_AXEL, Moves.SUCKER_PUNCH, Moves.WICKED_BLOW ],
[Species.FUECOCO]: [ Moves.ALLURING_VOICE, Moves.SLACK_OFF, Moves.OVERDRIVE, Moves.MOONGEIST_BEAM ], [Species.FUECOCO]: [ Moves.ALLURING_VOICE, Moves.SLACK_OFF, Moves.OVERDRIVE, Moves.MOONGEIST_BEAM ],
[Species.QUAXLY]: [ Moves.DRAGON_DANCE, Moves.TRIPLE_AXEL, Moves.POWER_TRIP, Moves.THUNDEROUS_KICK ], [Species.QUAXLY]: [ Moves.DRAGON_DANCE, Moves.TRIPLE_AXEL, Moves.POWER_TRIP, Moves.THUNDEROUS_KICK ],
[Species.LECHONK]: [ Moves.MILK_DRINK, Moves.PSYSHIELD_BASH, Moves.FILLET_AWAY, Moves.MULTI_ATTACK ], [Species.LECHONK]: [ Moves.MILK_DRINK, Moves.PSYSHIELD_BASH, Moves.FILLET_AWAY, Moves.MULTI_ATTACK ],
[Species.TAROUNTULA]: [ Moves.STONE_AXE, Moves.LEECH_LIFE, Moves.THIEF, Moves.SPORE ], [Species.TAROUNTULA]: [ Moves.STONE_AXE, Moves.LEECH_LIFE, Moves.THIEF, Moves.SPORE ],
[Species.NYMBLE]: [ Moves.KNOCK_OFF, Moves.FELL_STINGER, Moves.ATTACK_ORDER, Moves.WICKED_BLOW ], [Species.NYMBLE]: [ Moves.KNOCK_OFF, Moves.FELL_STINGER, Moves.ATTACK_ORDER, Moves.WICKED_BLOW ],
[Species.PAWMI]: [ Moves.DRAIN_PUNCH, Moves.ICE_PUNCH, Moves.MACH_PUNCH, Moves.PLASMA_FISTS ], [Species.PAWMI]: [ Moves.DRAIN_PUNCH, Moves.METEOR_MASH, Moves.JET_PUNCH, Moves.PLASMA_FISTS ],
[Species.TANDEMAUS]: [ Moves.BATON_PASS, Moves.THIEF, Moves.SIZZLY_SLIDE, Moves.REVIVAL_BLESSING ], [Species.TANDEMAUS]: [ Moves.BATON_PASS, Moves.COVET, Moves.SIZZLY_SLIDE, Moves.REVIVAL_BLESSING ],
[Species.FIDOUGH]: [ Moves.SOFT_BOILED, Moves.HIGH_HORSEPOWER, Moves.SIZZLY_SLIDE, Moves.TIDY_UP ], [Species.FIDOUGH]: [ Moves.SOFT_BOILED, Moves.HIGH_HORSEPOWER, Moves.SIZZLY_SLIDE, Moves.TIDY_UP ],
[Species.SMOLIV]: [ Moves.STRENGTH_SAP, Moves.EARTH_POWER, Moves.CALM_MIND, Moves.BOOMBURST ], [Species.SMOLIV]: [ Moves.STRENGTH_SAP, Moves.EARTH_POWER, Moves.CALM_MIND, Moves.BOOMBURST ],
[Species.SQUAWKABILLY]: [ Moves.PARTING_SHOT, Moves.EARTHQUAKE, Moves.FLARE_BLITZ, Moves.EXTREME_SPEED ], [Species.SQUAWKABILLY]: [ Moves.PARTING_SHOT, Moves.EARTHQUAKE, Moves.FLARE_BLITZ, Moves.EXTREME_SPEED ],
@ -497,24 +530,24 @@ export const speciesEggMoves = {
[Species.CAPSAKID]: [ Moves.STRENGTH_SAP, Moves.APPLE_ACID, Moves.FROST_BREATH, Moves.TORCH_SONG ], [Species.CAPSAKID]: [ Moves.STRENGTH_SAP, Moves.APPLE_ACID, Moves.FROST_BREATH, Moves.TORCH_SONG ],
[Species.RELLOR]: [ Moves.HEAL_BLOCK, Moves.RECOVER, Moves.HEAT_WAVE, Moves.LUMINA_CRASH ], [Species.RELLOR]: [ Moves.HEAL_BLOCK, Moves.RECOVER, Moves.HEAT_WAVE, Moves.LUMINA_CRASH ],
[Species.FLITTLE]: [ Moves.COSMIC_POWER, Moves.AURA_SPHERE, Moves.ROOST, Moves.FIERY_DANCE ], [Species.FLITTLE]: [ Moves.COSMIC_POWER, Moves.AURA_SPHERE, Moves.ROOST, Moves.FIERY_DANCE ],
[Species.TINKATINK]: [ Moves.MAGICAL_TORQUE, Moves.PYRO_BALL, Moves.ICE_HAMMER, Moves.SHIFT_GEAR ], [Species.TINKATINK]: [ Moves.MAGICAL_TORQUE, Moves.PYRO_BALL, Moves.IVY_CUDGEL, Moves.SHIFT_GEAR ],
[Species.WIGLETT]: [ Moves.SHELL_SMASH, Moves.ICICLE_CRASH, Moves.SEED_BOMB, Moves.SURGING_STRIKES ], [Species.WIGLETT]: [ Moves.SHELL_SMASH, Moves.ICICLE_CRASH, Moves.SEED_BOMB, Moves.SURGING_STRIKES ],
[Species.BOMBIRDIER]: [ Moves.FLOATY_FALL, Moves.SWORDS_DANCE, Moves.SUCKER_PUNCH, Moves.MIGHTY_CLEAVE ], [Species.BOMBIRDIER]: [ Moves.FLOATY_FALL, Moves.SWORDS_DANCE, Moves.SUCKER_PUNCH, Moves.MIGHTY_CLEAVE ],
[Species.FINIZEN]: [ Moves.TRIPLE_AXEL, Moves.DRAIN_PUNCH, Moves.HEADLONG_RUSH, Moves.SURGING_STRIKES ], [Species.FINIZEN]: [ Moves.TRIPLE_AXEL, Moves.DRAIN_PUNCH, Moves.HEADLONG_RUSH, Moves.SURGING_STRIKES ],
[Species.VAROOM]: [ Moves.COMBAT_TORQUE, Moves.U_TURN, Moves.BLAZING_TORQUE, Moves.NOXIOUS_TORQUE ], [Species.VAROOM]: [ Moves.COMBAT_TORQUE, Moves.U_TURN, Moves.BLAZING_TORQUE, Moves.NOXIOUS_TORQUE ],
[Species.CYCLIZAR]: [ Moves.BATON_PASS, Moves.BLAZING_TORQUE, Moves.KNOCK_OFF, Moves.CLANGOROUS_SOUL ], [Species.CYCLIZAR]: [ Moves.PARTING_SHOT, Moves.FIRE_LASH, Moves.MAGICAL_TORQUE, Moves.GLAIVE_RUSH ],
[Species.ORTHWORM]: [ Moves.SIZZLY_SLIDE, Moves.COIL, Moves.BODY_PRESS, Moves.SHORE_UP ], [Species.ORTHWORM]: [ Moves.SIZZLY_SLIDE, Moves.COIL, Moves.BODY_PRESS, Moves.SHORE_UP ],
[Species.GLIMMET]: [ Moves.CALM_MIND, Moves.EARTH_POWER, Moves.FIERY_DANCE, Moves.MALIGNANT_CHAIN ], [Species.GLIMMET]: [ Moves.CALM_MIND, Moves.EARTH_POWER, Moves.FIERY_DANCE, Moves.MALIGNANT_CHAIN ],
[Species.GREAVARD]: [ Moves.SHADOW_BONE, Moves.YAWN, Moves.SHORE_UP, Moves.COLLISION_COURSE ], [Species.GREAVARD]: [ Moves.SHADOW_BONE, Moves.YAWN, Moves.SHORE_UP, Moves.COLLISION_COURSE ],
[Species.FLAMIGO]: [ Moves.THUNDEROUS_KICK, Moves.TRIPLE_AXEL, Moves.FLOATY_FALL, Moves.VICTORY_DANCE ], [Species.FLAMIGO]: [ Moves.THUNDEROUS_KICK, Moves.TRIPLE_AXEL, Moves.FLOATY_FALL, Moves.VICTORY_DANCE ],
[Species.CETODDLE]: [ Moves.MOUNTAIN_GALE, Moves.HIGH_HORSEPOWER, Moves.RECOVER, Moves.DRAGON_DANCE ], [Species.CETODDLE]: [ Moves.MOUNTAIN_GALE, Moves.HIGH_HORSEPOWER, Moves.SLACK_OFF, Moves.DRAGON_DANCE ],
[Species.VELUZA]: [ Moves.PSYBLADE, Moves.FLIP_TURN, Moves.ICE_SPINNER, Moves.BITTER_BLADE ], [Species.VELUZA]: [ Moves.PSYBLADE, Moves.FLIP_TURN, Moves.ICE_SPINNER, Moves.BITTER_BLADE ],
[Species.DONDOZO]: [ Moves.SOFT_BOILED, Moves.SIZZLY_SLIDE, Moves.TOXIC, Moves.SALT_CURE ], [Species.DONDOZO]: [ Moves.SOFT_BOILED, Moves.SIZZLY_SLIDE, Moves.BREAKING_SWIPE, Moves.SALT_CURE ],
[Species.TATSUGIRI]: [ Moves.ICE_BEAM, Moves.FILLET_AWAY, Moves.CORE_ENFORCER, Moves.STEAM_ERUPTION ], [Species.TATSUGIRI]: [ Moves.SLUDGE_BOMB, Moves.FILLET_AWAY, Moves.CORE_ENFORCER, Moves.STEAM_ERUPTION ],
[Species.GREAT_TUSK]: [ Moves.STONE_AXE, Moves.MORNING_SUN, Moves.COLLISION_COURSE, Moves.SHIFT_GEAR ], [Species.GREAT_TUSK]: [ Moves.STONE_AXE, Moves.MORNING_SUN, Moves.COLLISION_COURSE, Moves.SHIFT_GEAR ],
[Species.SCREAM_TAIL]: [ Moves.TORCH_SONG, Moves.GLITZY_GLOW, Moves.MOONLIGHT, Moves.SPARKLY_SWIRL ], [Species.SCREAM_TAIL]: [ Moves.TORCH_SONG, Moves.GLITZY_GLOW, Moves.MOONLIGHT, Moves.SPARKLY_SWIRL ],
[Species.BRUTE_BONNET]: [ Moves.SAPPY_SEED, Moves.STRENGTH_SAP, Moves.EARTHQUAKE, Moves.WICKED_BLOW ], [Species.BRUTE_BONNET]: [ Moves.SAPPY_SEED, Moves.STRENGTH_SAP, Moves.EARTHQUAKE, Moves.WICKED_BLOW ],
[Species.FLUTTER_MANE]: [ Moves.MOONLIGHT, Moves.FLAMETHROWER, Moves.EARTH_POWER, Moves.ASTRAL_BARRAGE ], [Species.FLUTTER_MANE]: [ Moves.MOONLIGHT, Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.MOONGEIST_BEAM ],
[Species.SLITHER_WING]: [ Moves.MIGHTY_CLEAVE, Moves.THUNDEROUS_KICK, Moves.FIRE_LASH, Moves.VICTORY_DANCE ], [Species.SLITHER_WING]: [ Moves.MIGHTY_CLEAVE, Moves.THUNDEROUS_KICK, Moves.FIRE_LASH, Moves.VICTORY_DANCE ],
[Species.SANDY_SHOCKS]: [ Moves.MORNING_SUN, Moves.ICE_BEAM, Moves.NASTY_PLOT, Moves.THUNDERCLAP ], [Species.SANDY_SHOCKS]: [ Moves.MORNING_SUN, Moves.ICE_BEAM, Moves.NASTY_PLOT, Moves.THUNDERCLAP ],
[Species.IRON_TREADS]: [ Moves.FUSION_BOLT, Moves.BULK_UP, Moves.SHORE_UP, Moves.SUNSTEEL_STRIKE ], [Species.IRON_TREADS]: [ Moves.FUSION_BOLT, Moves.BULK_UP, Moves.SHORE_UP, Moves.SUNSTEEL_STRIKE ],
@ -523,57 +556,32 @@ export const speciesEggMoves = {
[Species.IRON_JUGULIS]: [ Moves.FIERY_WRATH, Moves.ROOST, Moves.NASTY_PLOT, Moves.OBLIVION_WING ], [Species.IRON_JUGULIS]: [ Moves.FIERY_WRATH, Moves.ROOST, Moves.NASTY_PLOT, Moves.OBLIVION_WING ],
[Species.IRON_MOTH]: [ Moves.EARTH_POWER, Moves.SEARING_SHOT, Moves.MALIGNANT_CHAIN, Moves.QUIVER_DANCE ], [Species.IRON_MOTH]: [ Moves.EARTH_POWER, Moves.SEARING_SHOT, Moves.MALIGNANT_CHAIN, Moves.QUIVER_DANCE ],
[Species.IRON_THORNS]: [ Moves.DIAMOND_STORM, Moves.SHORE_UP, Moves.SHIFT_GEAR, Moves.PLASMA_FISTS ], [Species.IRON_THORNS]: [ Moves.DIAMOND_STORM, Moves.SHORE_UP, Moves.SHIFT_GEAR, Moves.PLASMA_FISTS ],
[Species.FRIGIBAX]: [ Moves.DRAGON_DARTS, Moves.DRAGON_DANCE, Moves.EARTHQUAKE, Moves.GLACIAL_LANCE ], [Species.FRIGIBAX]: [ Moves.BEHEMOTH_BLADE, Moves.DRAGON_DANCE, Moves.MOUNTAIN_GALE, Moves.PRECIPICE_BLADES ],
[Species.GIMMIGHOUL]: [ Moves.HAPPY_HOUR, Moves.AURA_SPHERE, Moves.SURF, Moves.ASTRAL_BARRAGE ], [Species.GIMMIGHOUL]: [ Moves.HAPPY_HOUR, Moves.AURA_SPHERE, Moves.SURF, Moves.ASTRAL_BARRAGE ],
[Species.WO_CHIEN]: [ Moves.SPORE, Moves.FIERY_WRATH, Moves.SAPPY_SEED, Moves.STRENGTH_SAP ], [Species.WO_CHIEN]: [ Moves.SPORE, Moves.FIERY_WRATH, Moves.SAPPY_SEED, Moves.STRENGTH_SAP ],
[Species.CHIEN_PAO]: [ Moves.KNOCK_OFF, Moves.PARTING_SHOT, Moves.BITTER_BLADE, Moves.GLACIAL_LANCE ], [Species.CHIEN_PAO]: [ Moves.KNOCK_OFF, Moves.PARTING_SHOT, Moves.TRIPLE_AXEL, Moves.BITTER_BLADE ],
[Species.TING_LU]: [ Moves.SHORE_UP, Moves.WICKED_BLOW, Moves.SAPPY_SEED, Moves.THOUSAND_ARROWS ], [Species.TING_LU]: [ Moves.SHORE_UP, Moves.CEASELESS_EDGE, Moves.SAPPY_SEED, Moves.PRECIPICE_BLADES ],
[Species.CHI_YU]: [ Moves.FIERY_WRATH, Moves.HYDRO_STEAM, Moves.MORNING_SUN, Moves.BLUE_FLARE ], [Species.CHI_YU]: [ Moves.FIERY_WRATH, Moves.HYDRO_STEAM, Moves.MORNING_SUN, Moves.BLUE_FLARE ],
[Species.ROARING_MOON]: [ Moves.FIRE_LASH, Moves.DRAGON_HAMMER, Moves.SUCKER_PUNCH, Moves.WICKED_BLOW ], [Species.ROARING_MOON]: [ Moves.FIRE_LASH, Moves.DRAGON_HAMMER, Moves.SUCKER_PUNCH, Moves.WICKED_BLOW ],
[Species.IRON_VALIANT]: [ Moves.PLASMA_FISTS, Moves.NO_RETREAT, Moves.SECRET_SWORD, Moves.MAGICAL_TORQUE ], [Species.IRON_VALIANT]: [ Moves.PLASMA_FISTS, Moves.NO_RETREAT, Moves.SECRET_SWORD, Moves.MAGICAL_TORQUE ],
[Species.KORAIDON]: [ Moves.SUNSTEEL_STRIKE, Moves.MORNING_SUN, Moves.DRAGON_DARTS, Moves.BITTER_BLADE ], [Species.KORAIDON]: [ Moves.SUNSTEEL_STRIKE, Moves.SOLAR_BLADE, Moves.DRAGON_DARTS, Moves.BITTER_BLADE ],
[Species.MIRAIDON]: [ Moves.ICE_BEAM, Moves.CLANGOROUS_SOUL, Moves.CORE_ENFORCER, Moves.RISING_VOLTAGE ], [Species.MIRAIDON]: [ Moves.ICE_BEAM, Moves.CLANGOROUS_SOUL, Moves.CORE_ENFORCER, Moves.RISING_VOLTAGE ],
[Species.WALKING_WAKE]: [ Moves.CORE_ENFORCER, Moves.NASTY_PLOT, Moves.EARTH_POWER, Moves.BOUNCY_BUBBLE ], [Species.WALKING_WAKE]: [ Moves.BOUNCY_BUBBLE, Moves.NASTY_PLOT, Moves.SLUDGE_WAVE, Moves.CORE_ENFORCER ],
[Species.IRON_LEAVES]: [ Moves.BITTER_BLADE, Moves.U_TURN, Moves.MIGHTY_CLEAVE, Moves.VICTORY_DANCE ], [Species.IRON_LEAVES]: [ Moves.BITTER_BLADE, Moves.U_TURN, Moves.MIGHTY_CLEAVE, Moves.VICTORY_DANCE ],
[Species.POLTCHAGEIST]: [ Moves.SHELL_SMASH, Moves.BOUNCY_BUBBLE, Moves.LEECH_SEED, Moves.SPARKLY_SWIRL ], [Species.POLTCHAGEIST]: [ Moves.PARABOLIC_CHARGE, Moves.BOUNCY_BUBBLE, Moves.LEECH_SEED, Moves.SPARKLY_SWIRL ],
[Species.OKIDOGI]: [ Moves.DRAIN_PUNCH, Moves.KNOCK_OFF, Moves.DIRE_CLAW, Moves.VICTORY_DANCE ], [Species.OKIDOGI]: [ Moves.COMBAT_TORQUE, Moves.TIDY_UP, Moves.DIRE_CLAW, Moves.WICKED_BLOW ],
[Species.MUNKIDORI]: [ Moves.PSYSTRIKE, Moves.HEAT_WAVE, Moves.EARTH_POWER, Moves.MALIGNANT_CHAIN ], [Species.MUNKIDORI]: [ Moves.PSYSTRIKE, Moves.HEAT_WAVE, Moves.EARTH_POWER, Moves.MALIGNANT_CHAIN ],
[Species.FEZANDIPITI]: [ Moves.BARB_BARRAGE, Moves.VICTORY_DANCE, Moves.TRIPLE_AXEL, Moves.MAGICAL_TORQUE ], [Species.FEZANDIPITI]: [ Moves.BARB_BARRAGE, Moves.BONEMERANG, Moves.TRIPLE_AXEL, Moves.VICTORY_DANCE ],
[Species.OGERPON]: [ Moves.FLOWER_TRICK, Moves.BONEMERANG, Moves.TRIPLE_AXEL, Moves.GIGATON_HAMMER ], [Species.OGERPON]: [ Moves.SLEEP_POWDER, Moves.BONEMERANG, Moves.TRIPLE_AXEL, Moves.FLOWER_TRICK ],
[Species.GOUGING_FIRE]: [ Moves.EXTREME_SPEED, Moves.BULK_UP, Moves.SACRED_FIRE, Moves.GLAIVE_RUSH ], [Species.GOUGING_FIRE]: [ Moves.EXTREME_SPEED, Moves.BULK_UP, Moves.SACRED_FIRE, Moves.GLAIVE_RUSH ],
[Species.RAGING_BOLT]: [ Moves.NASTY_PLOT, Moves.FLAMETHROWER, Moves.MORNING_SUN, Moves.ELECTRO_DRIFT ], [Species.RAGING_BOLT]: [ Moves.NASTY_PLOT, Moves.FLAMETHROWER, Moves.MORNING_SUN, Moves.ELECTRO_DRIFT ],
[Species.IRON_BOULDER]: [ Moves.PSYBLADE, Moves.KOWTOW_CLEAVE, Moves.STONE_AXE, Moves.BITTER_BLADE ], [Species.IRON_BOULDER]: [ Moves.PSYBLADE, Moves.KOWTOW_CLEAVE, Moves.STONE_AXE, Moves.BITTER_BLADE ],
[Species.IRON_CROWN]: [ Moves.NASTY_PLOT, Moves.SECRET_SWORD, Moves.PSYSTRIKE, Moves.ELECTRO_DRIFT ], [Species.IRON_CROWN]: [ Moves.NASTY_PLOT, Moves.SECRET_SWORD, Moves.PSYSTRIKE, Moves.ELECTRO_DRIFT ],
[Species.TERAPAGOS]: [ Moves.MOONBLAST, Moves.RECOVER, Moves.ICE_BEAM, Moves.SHELL_SMASH ], [Species.TERAPAGOS]: [ Moves.MOONBLAST, Moves.RECOVER, Moves.ICE_BEAM, Moves.SHELL_SMASH ],
[Species.PECHARUNT]: [ Moves.TAKE_HEART, Moves.BODY_PRESS, Moves.SAPPY_SEED, Moves.KINGS_SHIELD ], [Species.PECHARUNT]: [ Moves.TAKE_HEART, Moves.BODY_PRESS, Moves.SAPPY_SEED, Moves.KINGS_SHIELD ],
[Species.ALOLA_RATTATA]: [ Moves.FALSE_SURRENDER, Moves.PSYCHIC_FANGS, Moves.COIL, Moves.EXTREME_SPEED ],
[Species.ALOLA_SANDSHREW]: [ Moves.SPIKY_SHIELD, Moves.AQUA_CUTTER, Moves.SHIFT_GEAR, Moves.GLACIAL_LANCE ],
[Species.ALOLA_VULPIX]: [ Moves.MOONBLAST, Moves.PARTING_SHOT, Moves.FLAMETHROWER, Moves.REVIVAL_BLESSING ],
[Species.ALOLA_DIGLETT]: [ Moves.THOUSAND_WAVES, Moves.SWORDS_DANCE, Moves.TRIPLE_DIVE, Moves.MOUNTAIN_GALE ],
[Species.ALOLA_MEOWTH]: [ Moves.BADDY_BAD, Moves.BUZZY_BUZZ, Moves.PARTING_SHOT, Moves.MAKE_IT_RAIN ],
[Species.ALOLA_GEODUDE]: [ Moves.THOUSAND_WAVES, Moves.BULK_UP, Moves.STONE_AXE, Moves.EXTREME_SPEED ],
[Species.ALOLA_GRIMER]: [ Moves.SUCKER_PUNCH, Moves.BARB_BARRAGE, Moves.STRENGTH_SAP, Moves.SURGING_STRIKES ],
[Species.ETERNAL_FLOETTE]: [ Moves.MIND_BLOWN, Moves.CHLOROBLAST, Moves.PHOTON_GEYSER, Moves.QUIVER_DANCE ],
[Species.GALAR_MEOWTH]: [ Moves.AQUA_CUTTER, Moves.KNOCK_OFF, Moves.BULLET_PUNCH, Moves.BEHEMOTH_BASH ],
[Species.GALAR_PONYTA]: [ Moves.MAGICAL_TORQUE, Moves.EXTREME_SPEED, Moves.FLARE_BLITZ, Moves.PHOTON_GEYSER ],
[Species.GALAR_SLOWPOKE]: [ Moves.TRICK_ROOM, Moves.BADDY_BAD, Moves.MOONBLAST, Moves.TORCH_SONG ],
[Species.GALAR_FARFETCHD]: [ Moves.ROOST, Moves.SACRED_SWORD, Moves.KINGS_SHIELD, Moves.BEHEMOTH_BLADE ],
[Species.GALAR_ARTICUNO]: [ Moves.SECRET_SWORD, Moves.NIGHT_DAZE, Moves.ICE_BEAM, Moves.OBLIVION_WING ],
[Species.GALAR_ZAPDOS]: [ Moves.TIDY_UP, Moves.FLOATY_FALL, Moves.ROOST, Moves.BOLT_BEAK ],
[Species.GALAR_MOLTRES]: [ Moves.ROOST, Moves.SLUDGE_BOMB, Moves.FLAMETHROWER, Moves.OBLIVION_WING ],
[Species.GALAR_CORSOLA]: [ Moves.SHELL_SMASH, Moves.AURA_SPHERE, Moves.INFERNAL_PARADE, Moves.ASTRAL_BARRAGE ],
[Species.GALAR_ZIGZAGOON]: [ Moves.CEASELESS_EDGE, Moves.FACADE, Moves.PARTING_SHOT, Moves.EXTREME_SPEED ],
[Species.GALAR_DARUMAKA]: [ Moves.ICE_SPINNER, Moves.ENDURE, Moves.DRAIN_PUNCH, Moves.V_CREATE ],
[Species.GALAR_YAMASK]: [ Moves.STRENGTH_SAP, Moves.DIRE_CLAW, Moves.THOUSAND_WAVES, Moves.SPECTRAL_THIEF ],
[Species.GALAR_STUNFISK]: [ Moves.SPIKY_SHIELD, Moves.THOUSAND_ARROWS, Moves.STRENGTH_SAP, Moves.DOUBLE_IRON_BASH ],
[Species.HISUI_GROWLITHE]: [ Moves.WAVE_CRASH, Moves.HEAD_SMASH, Moves.VOLT_TACKLE, Moves.DRAGON_DANCE ],
[Species.HISUI_VOLTORB]: [ Moves.FROST_BREATH, Moves.NASTY_PLOT, Moves.APPLE_ACID, Moves.ELECTRO_DRIFT ],
[Species.HISUI_QWILFISH]: [ Moves.CEASELESS_EDGE, Moves.KNOCK_OFF, Moves.STRENGTH_SAP, Moves.FISHIOUS_REND ],
[Species.HISUI_SNEASEL]: [ Moves.THUNDEROUS_KICK, Moves.KNOCK_OFF, Moves.TRIPLE_AXEL, Moves.VICTORY_DANCE ],
[Species.HISUI_ZORUA]: [ Moves.MOONBLAST, Moves.HYPER_VOICE, Moves.PARTING_SHOT, Moves.BLOOD_MOON ],
[Species.PALDEA_TAUROS]: [ Moves.NO_RETREAT, Moves.BLAZING_TORQUE, Moves.AQUA_STEP, Moves.THUNDEROUS_KICK ], [Species.PALDEA_TAUROS]: [ Moves.NO_RETREAT, Moves.BLAZING_TORQUE, Moves.AQUA_STEP, Moves.THUNDEROUS_KICK ],
[Species.PALDEA_WOOPER]: [ Moves.RECOVER, Moves.STONE_AXE, Moves.BANEFUL_BUNKER, Moves.SAPPY_SEED ], [Species.PALDEA_WOOPER]: [ Moves.STONE_AXE, Moves.RECOVER, Moves.BANEFUL_BUNKER, Moves.BARB_BARRAGE ],
[Species.BLOODMOON_URSALUNA]: [ Moves.NASTY_PLOT, Moves.TRICK_ROOM, Moves.THUNDERBOLT, Moves.BOOMBURST ] [Species.BLOODMOON_URSALUNA]: [ Moves.NASTY_PLOT, Moves.ROCK_POLISH, Moves.SANDSEAR_STORM, Moves.BOOMBURST ]
}; };
function parseEggMoves(content: string): void { function parseEggMoves(content: string): void {

View File

@ -23,9 +23,9 @@ export const starterPassiveAbilities = {
[Species.MEOWTH]: Abilities.TOUGH_CLAWS, [Species.MEOWTH]: Abilities.TOUGH_CLAWS,
[Species.PSYDUCK]: Abilities.SIMPLE, [Species.PSYDUCK]: Abilities.SIMPLE,
[Species.MANKEY]: Abilities.IRON_FIST, [Species.MANKEY]: Abilities.IRON_FIST,
[Species.GROWLITHE]: Abilities.SPEED_BOOST, [Species.GROWLITHE]: Abilities.FLUFFY,
[Species.POLIWAG]: Abilities.NO_GUARD, [Species.POLIWAG]: Abilities.NO_GUARD,
[Species.ABRA]: Abilities.PSYCHIC_SURGE, [Species.ABRA]: Abilities.MAGICIAN,
[Species.MACHOP]: Abilities.QUICK_FEET, [Species.MACHOP]: Abilities.QUICK_FEET,
[Species.BELLSPROUT]: Abilities.FLOWER_GIFT, [Species.BELLSPROUT]: Abilities.FLOWER_GIFT,
[Species.TENTACOOL]: Abilities.TOXIC_CHAIN, [Species.TENTACOOL]: Abilities.TOXIC_CHAIN,
@ -41,7 +41,7 @@ export const starterPassiveAbilities = {
[Species.GASTLY]: Abilities.SHADOW_SHIELD, [Species.GASTLY]: Abilities.SHADOW_SHIELD,
[Species.ONIX]: Abilities.ROCKY_PAYLOAD, [Species.ONIX]: Abilities.ROCKY_PAYLOAD,
[Species.DROWZEE]: Abilities.MAGICIAN, [Species.DROWZEE]: Abilities.MAGICIAN,
[Species.KRABBY]: Abilities.THERMAL_EXCHANGE, [Species.KRABBY]: Abilities.UNBURDEN,
[Species.VOLTORB]: Abilities.TRANSISTOR, [Species.VOLTORB]: Abilities.TRANSISTOR,
[Species.EXEGGCUTE]: Abilities.RIPEN, [Species.EXEGGCUTE]: Abilities.RIPEN,
[Species.CUBONE]: Abilities.PARENTAL_BOND, [Species.CUBONE]: Abilities.PARENTAL_BOND,
@ -70,6 +70,7 @@ export const starterPassiveAbilities = {
[Species.DRATINI]: Abilities.AERILATE, [Species.DRATINI]: Abilities.AERILATE,
[Species.MEWTWO]: Abilities.NEUROFORCE, [Species.MEWTWO]: Abilities.NEUROFORCE,
[Species.MEW]: Abilities.PROTEAN, [Species.MEW]: Abilities.PROTEAN,
[Species.CHIKORITA]: Abilities.THICK_FAT, [Species.CHIKORITA]: Abilities.THICK_FAT,
[Species.CYNDAQUIL]: Abilities.DROUGHT, [Species.CYNDAQUIL]: Abilities.DROUGHT,
[Species.TOTODILE]: Abilities.TOUGH_CLAWS, [Species.TOTODILE]: Abilities.TOUGH_CLAWS,
@ -77,12 +78,12 @@ export const starterPassiveAbilities = {
[Species.HOOTHOOT]: Abilities.AERILATE, [Species.HOOTHOOT]: Abilities.AERILATE,
[Species.LEDYBA]: Abilities.PRANKSTER, [Species.LEDYBA]: Abilities.PRANKSTER,
[Species.SPINARAK]: Abilities.PRANKSTER, [Species.SPINARAK]: Abilities.PRANKSTER,
[Species.CHINCHOU]: Abilities.WATER_BUBBLE, [Species.CHINCHOU]: Abilities.REGENERATOR,
[Species.PICHU]: Abilities.ELECTRIC_SURGE, [Species.PICHU]: Abilities.ELECTRIC_SURGE,
[Species.CLEFFA]: Abilities.ANALYTIC, [Species.CLEFFA]: Abilities.ANALYTIC,
[Species.IGGLYBUFF]: Abilities.HUGE_POWER, [Species.IGGLYBUFF]: Abilities.HUGE_POWER,
[Species.TOGEPI]: Abilities.PIXILATE, [Species.TOGEPI]: Abilities.PIXILATE,
[Species.NATU]: Abilities.TINTED_LENS, [Species.NATU]: Abilities.SHEER_FORCE,
[Species.MAREEP]: Abilities.ELECTROMORPHOSIS, [Species.MAREEP]: Abilities.ELECTROMORPHOSIS,
[Species.HOPPIP]: Abilities.FLUFFY, [Species.HOPPIP]: Abilities.FLUFFY,
[Species.AIPOM]: Abilities.SCRAPPY, [Species.AIPOM]: Abilities.SCRAPPY,
@ -108,24 +109,25 @@ export const starterPassiveAbilities = {
[Species.REMORAID]: Abilities.SIMPLE, [Species.REMORAID]: Abilities.SIMPLE,
[Species.DELIBIRD]: Abilities.HUGE_POWER, [Species.DELIBIRD]: Abilities.HUGE_POWER,
[Species.SKARMORY]: Abilities.LIGHTNING_ROD, [Species.SKARMORY]: Abilities.LIGHTNING_ROD,
[Species.HOUNDOUR]: Abilities.DROUGHT, [Species.HOUNDOUR]: Abilities.LIGHTNING_ROD,
[Species.PHANPY]: Abilities.SPEED_BOOST, [Species.PHANPY]: Abilities.SPEED_BOOST,
[Species.STANTLER]: Abilities.SPEED_BOOST, [Species.STANTLER]: Abilities.SPEED_BOOST,
[Species.SMEARGLE]: Abilities.PRANKSTER, [Species.SMEARGLE]: Abilities.PRANKSTER,
[Species.TYROGUE]: Abilities.MOXIE, [Species.TYROGUE]: Abilities.MOXIE,
[Species.SMOOCHUM]: Abilities.PSYCHIC_SURGE, [Species.SMOOCHUM]: Abilities.PSYCHIC_SURGE,
[Species.ELEKID]: Abilities.SHEER_FORCE, [Species.ELEKID]: Abilities.SHEER_FORCE,
[Species.MAGBY]: Abilities.CONTRARY, [Species.MAGBY]: Abilities.SHEER_FORCE,
[Species.MILTANK]: Abilities.STAMINA, [Species.MILTANK]: Abilities.STAMINA,
[Species.RAIKOU]: Abilities.TRANSISTOR, [Species.RAIKOU]: Abilities.BEAST_BOOST,
[Species.ENTEI]: Abilities.MOXIE, [Species.ENTEI]: Abilities.BEAST_BOOST,
[Species.SUICUNE]: Abilities.UNAWARE, [Species.SUICUNE]: Abilities.BEAST_BOOST,
[Species.LARVITAR]: Abilities.SAND_RUSH, [Species.LARVITAR]: Abilities.SAND_RUSH,
[Species.LUGIA]: Abilities.DELTA_STREAM, [Species.LUGIA]: Abilities.DELTA_STREAM,
[Species.HO_OH]: Abilities.MAGIC_GUARD, [Species.HO_OH]: Abilities.MAGIC_GUARD,
[Species.CELEBI]: Abilities.PSYCHIC_SURGE, [Species.CELEBI]: Abilities.PSYCHIC_SURGE,
[Species.TREECKO]: Abilities.TINTED_LENS, [Species.TREECKO]: Abilities.TINTED_LENS,
[Species.TORCHIC]: Abilities.RECKLESS, [Species.TORCHIC]: Abilities.DEFIANT,
[Species.MUDKIP]: Abilities.DRIZZLE, [Species.MUDKIP]: Abilities.DRIZZLE,
[Species.POOCHYENA]: Abilities.TOUGH_CLAWS, [Species.POOCHYENA]: Abilities.TOUGH_CLAWS,
[Species.ZIGZAGOON]: Abilities.RUN_AWAY, [Species.ZIGZAGOON]: Abilities.RUN_AWAY,
@ -148,7 +150,7 @@ export const starterPassiveAbilities = {
[Species.MAWILE]: Abilities.UNNERVE, [Species.MAWILE]: Abilities.UNNERVE,
[Species.ARON]: Abilities.EARTH_EATER, [Species.ARON]: Abilities.EARTH_EATER,
[Species.MEDITITE]: Abilities.MINDS_EYE, [Species.MEDITITE]: Abilities.MINDS_EYE,
[Species.ELECTRIKE]: Abilities.ELECTRIC_SURGE, [Species.ELECTRIKE]: Abilities.FLASH_FIRE,
[Species.PLUSLE]: Abilities.POWER_SPOT, [Species.PLUSLE]: Abilities.POWER_SPOT,
[Species.MINUN]: Abilities.POWER_SPOT, [Species.MINUN]: Abilities.POWER_SPOT,
[Species.VOLBEAT]: Abilities.HONEY_GATHER, [Species.VOLBEAT]: Abilities.HONEY_GATHER,
@ -162,7 +164,7 @@ export const starterPassiveAbilities = {
[Species.SPINDA]: Abilities.SIMPLE, [Species.SPINDA]: Abilities.SIMPLE,
[Species.TRAPINCH]: Abilities.ADAPTABILITY, [Species.TRAPINCH]: Abilities.ADAPTABILITY,
[Species.CACNEA]: Abilities.SAND_RUSH, [Species.CACNEA]: Abilities.SAND_RUSH,
[Species.SWABLU]: Abilities.ADAPTABILITY, [Species.SWABLU]: Abilities.FLUFFY,
[Species.ZANGOOSE]: Abilities.POISON_HEAL, [Species.ZANGOOSE]: Abilities.POISON_HEAL,
[Species.SEVIPER]: Abilities.MULTISCALE, [Species.SEVIPER]: Abilities.MULTISCALE,
[Species.LUNATONE]: Abilities.SHADOW_SHIELD, [Species.LUNATONE]: Abilities.SHADOW_SHIELD,
@ -182,14 +184,14 @@ export const starterPassiveAbilities = {
[Species.WYNAUT]: Abilities.STURDY, [Species.WYNAUT]: Abilities.STURDY,
[Species.SNORUNT]: Abilities.SNOW_WARNING, [Species.SNORUNT]: Abilities.SNOW_WARNING,
[Species.SPHEAL]: Abilities.UNAWARE, [Species.SPHEAL]: Abilities.UNAWARE,
[Species.CLAMPERL]: Abilities.DRIZZLE, [Species.CLAMPERL]: Abilities.ARENA_TRAP,
[Species.RELICANTH]: Abilities.PRIMORDIAL_SEA, [Species.RELICANTH]: Abilities.PRIMORDIAL_SEA,
[Species.LUVDISC]: Abilities.MULTISCALE, [Species.LUVDISC]: Abilities.MULTISCALE,
[Species.BAGON]: Abilities.DRAGONS_MAW, [Species.BAGON]: Abilities.MOLD_BREAKER,
[Species.BELDUM]: Abilities.LEVITATE, [Species.BELDUM]: Abilities.LEVITATE,
[Species.REGIROCK]: Abilities.SAND_STREAM, [Species.REGIROCK]: Abilities.SAND_STREAM,
[Species.REGICE]: Abilities.SNOW_WARNING, [Species.REGICE]: Abilities.SNOW_WARNING,
[Species.REGISTEEL]: Abilities.FILTER, [Species.REGISTEEL]: Abilities.STEELY_SPIRIT,
[Species.LATIAS]: Abilities.PRISM_ARMOR, [Species.LATIAS]: Abilities.PRISM_ARMOR,
[Species.LATIOS]: Abilities.TINTED_LENS, [Species.LATIOS]: Abilities.TINTED_LENS,
[Species.KYOGRE]: Abilities.MOLD_BREAKER, [Species.KYOGRE]: Abilities.MOLD_BREAKER,
@ -197,6 +199,7 @@ export const starterPassiveAbilities = {
[Species.RAYQUAZA]: Abilities.UNNERVE, [Species.RAYQUAZA]: Abilities.UNNERVE,
[Species.JIRACHI]: Abilities.COMATOSE, [Species.JIRACHI]: Abilities.COMATOSE,
[Species.DEOXYS]: Abilities.PROTEAN, [Species.DEOXYS]: Abilities.PROTEAN,
[Species.TURTWIG]: Abilities.THICK_FAT, [Species.TURTWIG]: Abilities.THICK_FAT,
[Species.CHIMCHAR]: Abilities.BEAST_BOOST, [Species.CHIMCHAR]: Abilities.BEAST_BOOST,
[Species.PIPLUP]: Abilities.DRIZZLE, [Species.PIPLUP]: Abilities.DRIZZLE,
@ -218,9 +221,9 @@ export const starterPassiveAbilities = {
[Species.GLAMEOW]: Abilities.INTIMIDATE, [Species.GLAMEOW]: Abilities.INTIMIDATE,
[Species.CHINGLING]: Abilities.PUNK_ROCK, [Species.CHINGLING]: Abilities.PUNK_ROCK,
[Species.STUNKY]: Abilities.NEUTRALIZING_GAS, [Species.STUNKY]: Abilities.NEUTRALIZING_GAS,
[Species.BRONZOR]: Abilities.BULLETPROOF, [Species.BRONZOR]: Abilities.MIRROR_ARMOR,
[Species.BONSLY]: Abilities.SAP_SIPPER, [Species.BONSLY]: Abilities.SAP_SIPPER,
[Species.MIME_JR]: Abilities.OPPORTUNIST, [Species.MIME_JR]: Abilities.PRANKSTER,
[Species.HAPPINY]: Abilities.FUR_COAT, [Species.HAPPINY]: Abilities.FUR_COAT,
[Species.CHATOT]: Abilities.PUNK_ROCK, [Species.CHATOT]: Abilities.PUNK_ROCK,
[Species.SPIRITOMB]: Abilities.VESSEL_OF_RUIN, [Species.SPIRITOMB]: Abilities.VESSEL_OF_RUIN,
@ -233,7 +236,7 @@ export const starterPassiveAbilities = {
[Species.CARNIVINE]: Abilities.ARENA_TRAP, [Species.CARNIVINE]: Abilities.ARENA_TRAP,
[Species.FINNEON]: Abilities.WATER_BUBBLE, [Species.FINNEON]: Abilities.WATER_BUBBLE,
[Species.MANTYKE]: Abilities.UNAWARE, [Species.MANTYKE]: Abilities.UNAWARE,
[Species.SNOVER]: Abilities.THICK_FAT, [Species.SNOVER]: Abilities.GRASSY_SURGE,
[Species.ROTOM]: Abilities.HADRON_ENGINE, [Species.ROTOM]: Abilities.HADRON_ENGINE,
[Species.UXIE]: Abilities.UNAWARE, [Species.UXIE]: Abilities.UNAWARE,
[Species.MESPRIT]: Abilities.MOODY, [Species.MESPRIT]: Abilities.MOODY,
@ -249,6 +252,7 @@ export const starterPassiveAbilities = {
[Species.DARKRAI]: Abilities.UNNERVE, [Species.DARKRAI]: Abilities.UNNERVE,
[Species.SHAYMIN]: Abilities.WIND_RIDER, [Species.SHAYMIN]: Abilities.WIND_RIDER,
[Species.ARCEUS]: Abilities.ADAPTABILITY, [Species.ARCEUS]: Abilities.ADAPTABILITY,
[Species.VICTINI]: Abilities.SHEER_FORCE, [Species.VICTINI]: Abilities.SHEER_FORCE,
[Species.SNIVY]: Abilities.MULTISCALE, [Species.SNIVY]: Abilities.MULTISCALE,
[Species.TEPIG]: Abilities.ROCK_HEAD, [Species.TEPIG]: Abilities.ROCK_HEAD,
@ -264,7 +268,7 @@ export const starterPassiveAbilities = {
[Species.BLITZLE]: Abilities.ELECTRIC_SURGE, [Species.BLITZLE]: Abilities.ELECTRIC_SURGE,
[Species.ROGGENROLA]: Abilities.SOLID_ROCK, [Species.ROGGENROLA]: Abilities.SOLID_ROCK,
[Species.WOOBAT]: Abilities.OPPORTUNIST, [Species.WOOBAT]: Abilities.OPPORTUNIST,
[Species.DRILBUR]: Abilities.SAND_STREAM, [Species.DRILBUR]: Abilities.STURDY,
[Species.AUDINO]: Abilities.FRIEND_GUARD, [Species.AUDINO]: Abilities.FRIEND_GUARD,
[Species.TIMBURR]: Abilities.ROCKY_PAYLOAD, [Species.TIMBURR]: Abilities.ROCKY_PAYLOAD,
[Species.TYMPOLE]: Abilities.POISON_HEAL, [Species.TYMPOLE]: Abilities.POISON_HEAL,
@ -292,7 +296,7 @@ export const starterPassiveAbilities = {
[Species.DUCKLETT]: Abilities.DRIZZLE, [Species.DUCKLETT]: Abilities.DRIZZLE,
[Species.VANILLITE]: Abilities.SLUSH_RUSH, [Species.VANILLITE]: Abilities.SLUSH_RUSH,
[Species.DEERLING]: Abilities.FUR_COAT, [Species.DEERLING]: Abilities.FUR_COAT,
[Species.EMOLGA]: Abilities.TRANSISTOR, [Species.EMOLGA]: Abilities.SERENE_GRACE,
[Species.KARRABLAST]: Abilities.QUICK_DRAW, [Species.KARRABLAST]: Abilities.QUICK_DRAW,
[Species.FOONGUS]: Abilities.THICK_FAT, [Species.FOONGUS]: Abilities.THICK_FAT,
[Species.FRILLISH]: Abilities.POISON_HEAL, [Species.FRILLISH]: Abilities.POISON_HEAL,
@ -301,10 +305,10 @@ export const starterPassiveAbilities = {
[Species.FERROSEED]: Abilities.ROUGH_SKIN, [Species.FERROSEED]: Abilities.ROUGH_SKIN,
[Species.KLINK]: Abilities.STEELY_SPIRIT, [Species.KLINK]: Abilities.STEELY_SPIRIT,
[Species.TYNAMO]: Abilities.POISON_HEAL, [Species.TYNAMO]: Abilities.POISON_HEAL,
[Species.ELGYEM]: Abilities.PRISM_ARMOR, [Species.ELGYEM]: Abilities.BEADS_OF_RUIN,
[Species.LITWICK]: Abilities.SOUL_HEART, [Species.LITWICK]: Abilities.SHADOW_TAG,
[Species.AXEW]: Abilities.DRAGONS_MAW, [Species.AXEW]: Abilities.DRAGONS_MAW,
[Species.CUBCHOO]: Abilities.TOUGH_CLAWS, [Species.CUBCHOO]: Abilities.FUR_COAT,
[Species.CRYOGONAL]: Abilities.SNOW_WARNING, [Species.CRYOGONAL]: Abilities.SNOW_WARNING,
[Species.SHELMET]: Abilities.PROTEAN, [Species.SHELMET]: Abilities.PROTEAN,
[Species.STUNFISK]: Abilities.STORM_DRAIN, [Species.STUNFISK]: Abilities.STORM_DRAIN,
@ -331,6 +335,7 @@ export const starterPassiveAbilities = {
[Species.KELDEO]: Abilities.GRIM_NEIGH, [Species.KELDEO]: Abilities.GRIM_NEIGH,
[Species.MELOETTA]: Abilities.MINDS_EYE, [Species.MELOETTA]: Abilities.MINDS_EYE,
[Species.GENESECT]: Abilities.PROTEAN, [Species.GENESECT]: Abilities.PROTEAN,
[Species.CHESPIN]: Abilities.DAUNTLESS_SHIELD, [Species.CHESPIN]: Abilities.DAUNTLESS_SHIELD,
[Species.FENNEKIN]: Abilities.PSYCHIC_SURGE, [Species.FENNEKIN]: Abilities.PSYCHIC_SURGE,
[Species.FROAKIE]: Abilities.STAKEOUT, [Species.FROAKIE]: Abilities.STAKEOUT,
@ -345,11 +350,11 @@ export const starterPassiveAbilities = {
[Species.ESPURR]: Abilities.FUR_COAT, [Species.ESPURR]: Abilities.FUR_COAT,
[Species.HONEDGE]: Abilities.SHARPNESS, [Species.HONEDGE]: Abilities.SHARPNESS,
[Species.SPRITZEE]: Abilities.FUR_COAT, [Species.SPRITZEE]: Abilities.FUR_COAT,
[Species.SWIRLIX]: Abilities.WELL_BAKED_BODY, [Species.SWIRLIX]: Abilities.RIPEN,
[Species.INKAY]: Abilities.UNNERVE, [Species.INKAY]: Abilities.UNNERVE,
[Species.BINACLE]: Abilities.SAP_SIPPER, [Species.BINACLE]: Abilities.SAP_SIPPER,
[Species.SKRELP]: Abilities.DRAGONS_MAW, [Species.SKRELP]: Abilities.DRAGONS_MAW,
[Species.CLAUNCHER]: Abilities.SWIFT_SWIM, [Species.CLAUNCHER]: Abilities.PROTEAN,
[Species.HELIOPTILE]: Abilities.PROTEAN, [Species.HELIOPTILE]: Abilities.PROTEAN,
[Species.TYRUNT]: Abilities.RECKLESS, [Species.TYRUNT]: Abilities.RECKLESS,
[Species.AMAURA]: Abilities.ICE_SCALES, [Species.AMAURA]: Abilities.ICE_SCALES,
@ -364,10 +369,12 @@ export const starterPassiveAbilities = {
[Species.NOIBAT]: Abilities.PUNK_ROCK, [Species.NOIBAT]: Abilities.PUNK_ROCK,
[Species.XERNEAS]: Abilities.HARVEST, [Species.XERNEAS]: Abilities.HARVEST,
[Species.YVELTAL]: Abilities.SOUL_HEART, [Species.YVELTAL]: Abilities.SOUL_HEART,
[Species.ZYGARDE]: Abilities.HUGE_POWER, [Species.ZYGARDE]: Abilities.ADAPTABILITY,
[Species.DIANCIE]: Abilities.LEVITATE, [Species.DIANCIE]: Abilities.PRISM_ARMOR,
[Species.HOOPA]: Abilities.OPPORTUNIST, [Species.HOOPA]: Abilities.OPPORTUNIST,
[Species.VOLCANION]: Abilities.FILTER, [Species.VOLCANION]: Abilities.FILTER,
[Species.ETERNAL_FLOETTE]: Abilities.MAGIC_GUARD,
[Species.ROWLET]: Abilities.SNIPER, [Species.ROWLET]: Abilities.SNIPER,
[Species.LITTEN]: Abilities.OPPORTUNIST, [Species.LITTEN]: Abilities.OPPORTUNIST,
[Species.POPPLIO]: Abilities.PUNK_ROCK, [Species.POPPLIO]: Abilities.PUNK_ROCK,
@ -403,7 +410,7 @@ export const starterPassiveAbilities = {
[Species.DRAMPA]: Abilities.THICK_FAT, [Species.DRAMPA]: Abilities.THICK_FAT,
[Species.DHELMISE]: Abilities.WATER_BUBBLE, [Species.DHELMISE]: Abilities.WATER_BUBBLE,
[Species.JANGMO_O]: Abilities.DAUNTLESS_SHIELD, [Species.JANGMO_O]: Abilities.DAUNTLESS_SHIELD,
[Species.TAPU_KOKO]: Abilities.TRANSISTOR, [Species.TAPU_KOKO]: Abilities.DAUNTLESS_SHIELD,
[Species.TAPU_LELE]: Abilities.SHEER_FORCE, [Species.TAPU_LELE]: Abilities.SHEER_FORCE,
[Species.TAPU_BULU]: Abilities.TRIAGE, [Species.TAPU_BULU]: Abilities.TRIAGE,
[Species.TAPU_FINI]: Abilities.FAIRY_AURA, [Species.TAPU_FINI]: Abilities.FAIRY_AURA,
@ -413,16 +420,24 @@ export const starterPassiveAbilities = {
[Species.PHEROMOSA]: Abilities.TINTED_LENS, [Species.PHEROMOSA]: Abilities.TINTED_LENS,
[Species.XURKITREE]: Abilities.TRANSISTOR, [Species.XURKITREE]: Abilities.TRANSISTOR,
[Species.CELESTEELA]: Abilities.HEATPROOF, [Species.CELESTEELA]: Abilities.HEATPROOF,
[Species.KARTANA]: Abilities.SHARPNESS, [Species.KARTANA]: Abilities.LONG_REACH,
[Species.GUZZLORD]: Abilities.POISON_HEAL, [Species.GUZZLORD]: Abilities.POISON_HEAL,
[Species.NECROZMA]: Abilities.BEAST_BOOST, [Species.NECROZMA]: Abilities.BEAST_BOOST,
[Species.MAGEARNA]: Abilities.STEELY_SPIRIT, [Species.MAGEARNA]: Abilities.STEELY_SPIRIT,
[Species.MARSHADOW]: Abilities.IRON_FIST, [Species.MARSHADOW]: Abilities.IRON_FIST,
[Species.POIPOLE]: Abilities.SHEER_FORCE, [Species.POIPOLE]: Abilities.LEVITATE,
[Species.STAKATAKA]: Abilities.SOLID_ROCK, [Species.STAKATAKA]: Abilities.SOLID_ROCK,
[Species.BLACEPHALON]: Abilities.MAGIC_GUARD, [Species.BLACEPHALON]: Abilities.MAGIC_GUARD,
[Species.ZERAORA]: Abilities.TOUGH_CLAWS, [Species.ZERAORA]: Abilities.TOUGH_CLAWS,
[Species.MELTAN]: Abilities.STEELY_SPIRIT, [Species.MELTAN]: Abilities.HEATPROOF,
[Species.ALOLA_RATTATA]: Abilities.ADAPTABILITY,
[Species.ALOLA_SANDSHREW]: Abilities.ICE_SCALES,
[Species.ALOLA_VULPIX]: Abilities.SHEER_FORCE,
[Species.ALOLA_DIGLETT]: Abilities.STURDY,
[Species.ALOLA_MEOWTH]: Abilities.DARK_AURA,
[Species.ALOLA_GEODUDE]: Abilities.DRY_SKIN,
[Species.ALOLA_GRIMER]: Abilities.TOXIC_DEBRIS,
[Species.GROOKEY]: Abilities.GRASS_PELT, [Species.GROOKEY]: Abilities.GRASS_PELT,
[Species.SCORBUNNY]: Abilities.NO_GUARD, [Species.SCORBUNNY]: Abilities.NO_GUARD,
[Species.SOBBLE]: Abilities.SUPER_LUCK, [Species.SOBBLE]: Abilities.SUPER_LUCK,
@ -431,7 +446,7 @@ export const starterPassiveAbilities = {
[Species.BLIPBUG]: Abilities.PSYCHIC_SURGE, [Species.BLIPBUG]: Abilities.PSYCHIC_SURGE,
[Species.NICKIT]: Abilities.MAGICIAN, [Species.NICKIT]: Abilities.MAGICIAN,
[Species.GOSSIFLEUR]: Abilities.GRASSY_SURGE, [Species.GOSSIFLEUR]: Abilities.GRASSY_SURGE,
[Species.WOOLOO]: Abilities.SIMPLE, [Species.WOOLOO]: Abilities.SCRAPPY,
[Species.CHEWTLE]: Abilities.ROCKY_PAYLOAD, [Species.CHEWTLE]: Abilities.ROCKY_PAYLOAD,
[Species.YAMPER]: Abilities.SHEER_FORCE, [Species.YAMPER]: Abilities.SHEER_FORCE,
[Species.ROLYCOLY]: Abilities.SOLID_ROCK, [Species.ROLYCOLY]: Abilities.SOLID_ROCK,
@ -444,7 +459,7 @@ export const starterPassiveAbilities = {
[Species.CLOBBOPUS]: Abilities.WATER_BUBBLE, [Species.CLOBBOPUS]: Abilities.WATER_BUBBLE,
[Species.SINISTEA]: Abilities.SHADOW_SHIELD, [Species.SINISTEA]: Abilities.SHADOW_SHIELD,
[Species.HATENNA]: Abilities.FAIRY_AURA, [Species.HATENNA]: Abilities.FAIRY_AURA,
[Species.IMPIDIMP]: Abilities.FUR_COAT, [Species.IMPIDIMP]: Abilities.INTIMIDATE,
[Species.MILCERY]: Abilities.REGENERATOR, [Species.MILCERY]: Abilities.REGENERATOR,
[Species.FALINKS]: Abilities.PARENTAL_BOND, [Species.FALINKS]: Abilities.PARENTAL_BOND,
[Species.PINCURCHIN]: Abilities.ELECTROMORPHOSIS, [Species.PINCURCHIN]: Abilities.ELECTROMORPHOSIS,
@ -455,7 +470,7 @@ export const starterPassiveAbilities = {
[Species.MORPEKO]: Abilities.MOODY, [Species.MORPEKO]: Abilities.MOODY,
[Species.CUFANT]: Abilities.EARTH_EATER, [Species.CUFANT]: Abilities.EARTH_EATER,
[Species.DRACOZOLT]: Abilities.NO_GUARD, [Species.DRACOZOLT]: Abilities.NO_GUARD,
[Species.ARCTOZOLT]: Abilities.TRANSISTOR, [Species.ARCTOZOLT]: Abilities.WATER_ABSORB,
[Species.DRACOVISH]: Abilities.SWIFT_SWIM, [Species.DRACOVISH]: Abilities.SWIFT_SWIM,
[Species.ARCTOVISH]: Abilities.STRONG_JAW, [Species.ARCTOVISH]: Abilities.STRONG_JAW,
[Species.DURALUDON]: Abilities.STEELWORKER, [Species.DURALUDON]: Abilities.STEELWORKER,
@ -471,6 +486,24 @@ export const starterPassiveAbilities = {
[Species.SPECTRIER]: Abilities.SHADOW_SHIELD, [Species.SPECTRIER]: Abilities.SHADOW_SHIELD,
[Species.CALYREX]: Abilities.HARVEST, [Species.CALYREX]: Abilities.HARVEST,
[Species.ENAMORUS]: Abilities.FAIRY_AURA, [Species.ENAMORUS]: Abilities.FAIRY_AURA,
[Species.GALAR_MEOWTH]: Abilities.UNBURDEN,
[Species.GALAR_PONYTA]: Abilities.CHILLING_NEIGH,
[Species.GALAR_SLOWPOKE]: Abilities.UNAWARE,
[Species.GALAR_FARFETCHD]: Abilities.INTREPID_SWORD,
[Species.GALAR_ARTICUNO]: Abilities.SERENE_GRACE,
[Species.GALAR_ZAPDOS]: Abilities.TOUGH_CLAWS,
[Species.GALAR_MOLTRES]: Abilities.DARK_AURA,
[Species.GALAR_CORSOLA]: Abilities.SHADOW_SHIELD,
[Species.GALAR_ZIGZAGOON]: Abilities.POISON_HEAL,
[Species.GALAR_DARUMAKA]: Abilities.FLASH_FIRE,
[Species.GALAR_YAMASK]: Abilities.TABLETS_OF_RUIN,
[Species.GALAR_STUNFISK]: Abilities.ARENA_TRAP,
[Species.HISUI_GROWLITHE]: Abilities.RECKLESS,
[Species.HISUI_VOLTORB]: Abilities.TRANSISTOR,
[Species.HISUI_QWILFISH]: Abilities.MERCILESS,
[Species.HISUI_SNEASEL]: Abilities.SCRAPPY,
[Species.HISUI_ZORUA]: Abilities.ADAPTABILITY,
[Species.SPRIGATITO]: Abilities.MAGICIAN, [Species.SPRIGATITO]: Abilities.MAGICIAN,
[Species.FUECOCO]: Abilities.PUNK_ROCK, [Species.FUECOCO]: Abilities.PUNK_ROCK,
[Species.QUAXLY]: Abilities.OPPORTUNIST, [Species.QUAXLY]: Abilities.OPPORTUNIST,
@ -502,40 +535,40 @@ export const starterPassiveAbilities = {
[Species.CYCLIZAR]: Abilities.PROTEAN, [Species.CYCLIZAR]: Abilities.PROTEAN,
[Species.ORTHWORM]: Abilities.REGENERATOR, [Species.ORTHWORM]: Abilities.REGENERATOR,
[Species.GLIMMET]: Abilities.LEVITATE, [Species.GLIMMET]: Abilities.LEVITATE,
[Species.GREAVARD]: Abilities.FUR_COAT, [Species.GREAVARD]: Abilities.UNAWARE,
[Species.FLAMIGO]: Abilities.MOXIE, [Species.FLAMIGO]: Abilities.MOXIE,
[Species.CETODDLE]: Abilities.ICE_SCALES, [Species.CETODDLE]: Abilities.REFRIGERATE,
[Species.VELUZA]: Abilities.SUPER_LUCK, [Species.VELUZA]: Abilities.SUPER_LUCK,
[Species.DONDOZO]: Abilities.PARENTAL_BOND, [Species.DONDOZO]: Abilities.DRAGONS_MAW,
[Species.TATSUGIRI]: Abilities.ADAPTABILITY, [Species.TATSUGIRI]: Abilities.FLUFFY,
[Species.GREAT_TUSK]: Abilities.INTIMIDATE, [Species.GREAT_TUSK]: Abilities.INTIMIDATE,
[Species.SCREAM_TAIL]: Abilities.UNAWARE, [Species.SCREAM_TAIL]: Abilities.UNAWARE,
[Species.BRUTE_BONNET]: Abilities.CHLOROPHYLL, [Species.BRUTE_BONNET]: Abilities.CHLOROPHYLL,
[Species.FLUTTER_MANE]: Abilities.DAZZLING, [Species.FLUTTER_MANE]: Abilities.DAZZLING,
[Species.SLITHER_WING]: Abilities.SCRAPPY, [Species.SLITHER_WING]: Abilities.SCRAPPY,
[Species.SANDY_SHOCKS]: Abilities.EARTH_EATER, [Species.SANDY_SHOCKS]: Abilities.ELECTRIC_SURGE,
[Species.IRON_TREADS]: Abilities.STEELY_SPIRIT, [Species.IRON_TREADS]: Abilities.STEELY_SPIRIT,
[Species.IRON_BUNDLE]: Abilities.SNOW_WARNING, [Species.IRON_BUNDLE]: Abilities.SNOW_WARNING,
[Species.IRON_HANDS]: Abilities.IRON_FIST, [Species.IRON_HANDS]: Abilities.IRON_FIST,
[Species.IRON_JUGULIS]: Abilities.LIGHTNING_ROD, [Species.IRON_JUGULIS]: Abilities.LIGHTNING_ROD,
[Species.IRON_MOTH]: Abilities.LEVITATE, [Species.IRON_MOTH]: Abilities.LEVITATE,
[Species.IRON_THORNS]: Abilities.SAND_STREAM, [Species.IRON_THORNS]: Abilities.SAND_STREAM,
[Species.FRIGIBAX]: Abilities.SNOW_WARNING, [Species.FRIGIBAX]: Abilities.INTIMIDATE,
[Species.GIMMIGHOUL]: Abilities.HONEY_GATHER, [Species.GIMMIGHOUL]: Abilities.HONEY_GATHER,
[Species.WO_CHIEN]: Abilities.VESSEL_OF_RUIN, [Species.WO_CHIEN]: Abilities.VESSEL_OF_RUIN,
[Species.CHIEN_PAO]: Abilities.INTIMIDATE, [Species.CHIEN_PAO]: Abilities.INTIMIDATE,
[Species.TING_LU]: Abilities.STAMINA, [Species.TING_LU]: Abilities.STAMINA,
[Species.CHI_YU]: Abilities.BERSERK, [Species.CHI_YU]: Abilities.BERSERK,
[Species.ROARING_MOON]: Abilities.TOUGH_CLAWS, [Species.ROARING_MOON]: Abilities.TOUGH_CLAWS,
[Species.IRON_VALIANT]: Abilities.ADAPTABILITY, [Species.IRON_VALIANT]: Abilities.NEUROFORCE,
[Species.KORAIDON]: Abilities.OPPORTUNIST, [Species.KORAIDON]: Abilities.OPPORTUNIST,
[Species.MIRAIDON]: Abilities.OPPORTUNIST, [Species.MIRAIDON]: Abilities.OPPORTUNIST,
[Species.WALKING_WAKE]: Abilities.BEAST_BOOST, [Species.WALKING_WAKE]: Abilities.BEAST_BOOST,
[Species.IRON_LEAVES]: Abilities.SHARPNESS, [Species.IRON_LEAVES]: Abilities.SHARPNESS,
[Species.POLTCHAGEIST]: Abilities.TRIAGE, [Species.POLTCHAGEIST]: Abilities.TRIAGE,
[Species.OKIDOGI]: Abilities.FUR_COAT, [Species.OKIDOGI]: Abilities.DARK_AURA,
[Species.MUNKIDORI]: Abilities.NEUROFORCE, [Species.MUNKIDORI]: Abilities.MAGICIAN,
[Species.FEZANDIPITI]: Abilities.LEVITATE, [Species.FEZANDIPITI]: Abilities.PIXILATE,
[Species.OGERPON]: Abilities.OPPORTUNIST, [Species.OGERPON]: Abilities.OPPORTUNIST,
[Species.GOUGING_FIRE]: Abilities.BEAST_BOOST, [Species.GOUGING_FIRE]: Abilities.BEAST_BOOST,
[Species.RAGING_BOLT]: Abilities.BEAST_BOOST, [Species.RAGING_BOLT]: Abilities.BEAST_BOOST,
@ -543,31 +576,6 @@ export const starterPassiveAbilities = {
[Species.IRON_CROWN]: Abilities.SHARPNESS, [Species.IRON_CROWN]: Abilities.SHARPNESS,
[Species.TERAPAGOS]: Abilities.SOUL_HEART, [Species.TERAPAGOS]: Abilities.SOUL_HEART,
[Species.PECHARUNT]: Abilities.TOXIC_CHAIN, [Species.PECHARUNT]: Abilities.TOXIC_CHAIN,
[Species.ALOLA_RATTATA]: Abilities.ADAPTABILITY,
[Species.ALOLA_SANDSHREW]: Abilities.ICE_SCALES,
[Species.ALOLA_VULPIX]: Abilities.SHEER_FORCE,
[Species.ALOLA_DIGLETT]: Abilities.STURDY,
[Species.ALOLA_MEOWTH]: Abilities.DARK_AURA,
[Species.ALOLA_GEODUDE]: Abilities.DRY_SKIN,
[Species.ALOLA_GRIMER]: Abilities.TOXIC_DEBRIS,
[Species.ETERNAL_FLOETTE]: Abilities.MAGIC_GUARD,
[Species.GALAR_MEOWTH]: Abilities.STEELWORKER,
[Species.GALAR_PONYTA]: Abilities.MOXIE,
[Species.GALAR_SLOWPOKE]: Abilities.UNAWARE,
[Species.GALAR_FARFETCHD]: Abilities.INTREPID_SWORD,
[Species.GALAR_ARTICUNO]: Abilities.SERENE_GRACE,
[Species.GALAR_ZAPDOS]: Abilities.TOUGH_CLAWS,
[Species.GALAR_MOLTRES]: Abilities.DARK_AURA,
[Species.GALAR_CORSOLA]: Abilities.SHADOW_SHIELD,
[Species.GALAR_ZIGZAGOON]: Abilities.POISON_HEAL,
[Species.GALAR_DARUMAKA]: Abilities.FLASH_FIRE,
[Species.GALAR_YAMASK]: Abilities.TABLETS_OF_RUIN,
[Species.GALAR_STUNFISK]: Abilities.ARENA_TRAP,
[Species.HISUI_GROWLITHE]: Abilities.RECKLESS,
[Species.HISUI_VOLTORB]: Abilities.TRANSISTOR,
[Species.HISUI_QWILFISH]: Abilities.MERCILESS,
[Species.HISUI_SNEASEL]: Abilities.SCRAPPY,
[Species.HISUI_ZORUA]: Abilities.ADAPTABILITY,
[Species.PALDEA_TAUROS]: Abilities.ADAPTABILITY, [Species.PALDEA_TAUROS]: Abilities.ADAPTABILITY,
[Species.PALDEA_WOOPER]: Abilities.THICK_FAT, [Species.PALDEA_WOOPER]: Abilities.THICK_FAT,
[Species.BLOODMOON_URSALUNA]: Abilities.BERSERK [Species.BLOODMOON_URSALUNA]: Abilities.BERSERK

View File

@ -16,9 +16,9 @@ interface PokemonSpeciesFormLevelMoves {
} }
/** Moves that can only be learned with a memory-mushroom */ /** Moves that can only be learned with a memory-mushroom */
const RELEARN_MOVE = -1; export const RELEARN_MOVE = -1;
/** Moves that can only be learned with an evolve */ /** Moves that can only be learned with an evolve */
const EVOLVE_MOVE = 0; export const EVOLVE_MOVE = 0;
export const pokemonSpeciesLevelMoves: PokemonSpeciesLevelMoves = { export const pokemonSpeciesLevelMoves: PokemonSpeciesLevelMoves = {
[Species.BULBASAUR]: [ [Species.BULBASAUR]: [
@ -19464,7 +19464,6 @@ export const pokemonFormLevelMoves: PokemonSpeciesFormLevelMoves = {
}, },
[Species.GRENINJA]: { [Species.GRENINJA]: {
1: [ 1: [
[ EVOLVE_MOVE, Moves.WATER_SHURIKEN ],
[ EVOLVE_MOVE, Moves.WATER_SHURIKEN ], [ EVOLVE_MOVE, Moves.WATER_SHURIKEN ],
[ 1, Moves.POUND ], [ 1, Moves.POUND ],
[ 1, Moves.GROWL ], [ 1, Moves.GROWL ],
@ -19475,6 +19474,7 @@ export const pokemonFormLevelMoves: PokemonSpeciesFormLevelMoves = {
[ 1, Moves.SMACK_DOWN ], // Previous Stage Move [ 1, Moves.SMACK_DOWN ], // Previous Stage Move
[ 1, Moves.BOUNCE ], // Previous Stage Move [ 1, Moves.BOUNCE ], // Previous Stage Move
[ 1, Moves.HAZE ], [ 1, Moves.HAZE ],
[ 1, Moves.MAT_BLOCK ],
[ 1, Moves.ROLE_PLAY ], [ 1, Moves.ROLE_PLAY ],
[ 1, Moves.NIGHT_SLASH ], [ 1, Moves.NIGHT_SLASH ],
[ 10, Moves.LICK ], [ 10, Moves.LICK ],

View File

@ -0,0 +1,46 @@
import { Species } from "#enums/species";
/**
* A list of all {@link https://bulbapedia.bulbagarden.net/wiki/Paradox_Pok%C3%A9mon | Paradox Pokemon}, NOT including the legendaries Miraidon and Koraidon.
*/
export const NON_LEGEND_PARADOX_POKEMON = [
Species.GREAT_TUSK,
Species.SCREAM_TAIL,
Species.BRUTE_BONNET,
Species.FLUTTER_MANE,
Species.SLITHER_WING,
Species.SANDY_SHOCKS,
Species.ROARING_MOON,
Species.WALKING_WAKE,
Species.GOUGING_FIRE,
Species.RAGING_BOLT,
Species.IRON_TREADS,
Species.IRON_BUNDLE,
Species.IRON_HANDS,
Species.IRON_JUGULIS,
Species.IRON_MOTH,
Species.IRON_THORNS,
Species.IRON_VALIANT,
Species.IRON_LEAVES,
Species.IRON_BOULDER,
Species.IRON_CROWN,
];
/**
* A list of all {@link https://bulbapedia.bulbagarden.net/wiki/Ultra_Beast | Ultra Beasts}, NOT including legendaries such as Necrozma or the Cosmog line.
*
* Note that all of these Ultra Beasts are still considered Sub-Legendary.
*/
export const NON_LEGEND_ULTRA_BEASTS = [
Species.NIHILEGO,
Species.BUZZWOLE,
Species.PHEROMOSA,
Species.XURKITREE,
Species.CELESTEELA,
Species.KARTANA,
Species.GUZZLORD,
Species.POIPOLE,
Species.NAGANADEL,
Species.STAKATAKA,
Species.BLACEPHALON,
];

View File

@ -14,13 +14,10 @@ export const speciesEggTiers = {
[Species.RATTATA]: EggTier.COMMON, [Species.RATTATA]: EggTier.COMMON,
[Species.SPEAROW]: EggTier.COMMON, [Species.SPEAROW]: EggTier.COMMON,
[Species.EKANS]: EggTier.COMMON, [Species.EKANS]: EggTier.COMMON,
[Species.PIKACHU]: EggTier.COMMON,
[Species.SANDSHREW]: EggTier.COMMON, [Species.SANDSHREW]: EggTier.COMMON,
[Species.NIDORAN_F]: EggTier.COMMON, [Species.NIDORAN_F]: EggTier.COMMON,
[Species.NIDORAN_M]: EggTier.COMMON, [Species.NIDORAN_M]: EggTier.COMMON,
[Species.CLEFAIRY]: EggTier.COMMON,
[Species.VULPIX]: EggTier.COMMON, [Species.VULPIX]: EggTier.COMMON,
[Species.JIGGLYPUFF]: EggTier.COMMON,
[Species.ZUBAT]: EggTier.COMMON, [Species.ZUBAT]: EggTier.COMMON,
[Species.ODDISH]: EggTier.COMMON, [Species.ODDISH]: EggTier.COMMON,
[Species.PARAS]: EggTier.COMMON, [Species.PARAS]: EggTier.COMMON,
@ -39,7 +36,7 @@ export const speciesEggTiers = {
[Species.PONYTA]: EggTier.COMMON, [Species.PONYTA]: EggTier.COMMON,
[Species.SLOWPOKE]: EggTier.COMMON, [Species.SLOWPOKE]: EggTier.COMMON,
[Species.MAGNEMITE]: EggTier.RARE, [Species.MAGNEMITE]: EggTier.RARE,
[Species.FARFETCHD]: EggTier.COMMON, [Species.FARFETCHD]: EggTier.RARE,
[Species.DODUO]: EggTier.COMMON, [Species.DODUO]: EggTier.COMMON,
[Species.SEEL]: EggTier.COMMON, [Species.SEEL]: EggTier.COMMON,
[Species.GRIMER]: EggTier.COMMON, [Species.GRIMER]: EggTier.COMMON,
@ -51,33 +48,25 @@ export const speciesEggTiers = {
[Species.VOLTORB]: EggTier.COMMON, [Species.VOLTORB]: EggTier.COMMON,
[Species.EXEGGCUTE]: EggTier.COMMON, [Species.EXEGGCUTE]: EggTier.COMMON,
[Species.CUBONE]: EggTier.COMMON, [Species.CUBONE]: EggTier.COMMON,
[Species.HITMONLEE]: EggTier.RARE, [Species.LICKITUNG]: EggTier.RARE,
[Species.HITMONCHAN]: EggTier.RARE,
[Species.LICKITUNG]: EggTier.COMMON,
[Species.KOFFING]: EggTier.COMMON, [Species.KOFFING]: EggTier.COMMON,
[Species.RHYHORN]: EggTier.COMMON, [Species.RHYHORN]: EggTier.RARE,
[Species.CHANSEY]: EggTier.COMMON,
[Species.TANGELA]: EggTier.COMMON, [Species.TANGELA]: EggTier.COMMON,
[Species.KANGASKHAN]: EggTier.RARE, [Species.KANGASKHAN]: EggTier.RARE,
[Species.HORSEA]: EggTier.COMMON, [Species.HORSEA]: EggTier.COMMON,
[Species.GOLDEEN]: EggTier.COMMON, [Species.GOLDEEN]: EggTier.COMMON,
[Species.STARYU]: EggTier.COMMON, [Species.STARYU]: EggTier.COMMON,
[Species.MR_MIME]: EggTier.COMMON,
[Species.SCYTHER]: EggTier.RARE, [Species.SCYTHER]: EggTier.RARE,
[Species.JYNX]: EggTier.RARE,
[Species.ELECTABUZZ]: EggTier.RARE,
[Species.MAGMAR]: EggTier.RARE,
[Species.PINSIR]: EggTier.RARE, [Species.PINSIR]: EggTier.RARE,
[Species.TAUROS]: EggTier.RARE, [Species.TAUROS]: EggTier.RARE,
[Species.MAGIKARP]: EggTier.RARE, [Species.MAGIKARP]: EggTier.COMMON,
[Species.LAPRAS]: EggTier.RARE, [Species.LAPRAS]: EggTier.RARE,
[Species.DITTO]: EggTier.COMMON, [Species.DITTO]: EggTier.COMMON,
[Species.EEVEE]: EggTier.COMMON, [Species.EEVEE]: EggTier.COMMON,
[Species.PORYGON]: EggTier.RARE, [Species.PORYGON]: EggTier.RARE,
[Species.OMANYTE]: EggTier.COMMON, [Species.OMANYTE]: EggTier.RARE,
[Species.KABUTO]: EggTier.COMMON, [Species.KABUTO]: EggTier.RARE,
[Species.AERODACTYL]: EggTier.RARE, [Species.AERODACTYL]: EggTier.RARE,
[Species.SNORLAX]: EggTier.RARE,
[Species.ARTICUNO]: EggTier.EPIC, [Species.ARTICUNO]: EggTier.EPIC,
[Species.ZAPDOS]: EggTier.EPIC, [Species.ZAPDOS]: EggTier.EPIC,
[Species.MOLTRES]: EggTier.EPIC, [Species.MOLTRES]: EggTier.EPIC,
@ -93,14 +82,12 @@ export const speciesEggTiers = {
[Species.LEDYBA]: EggTier.COMMON, [Species.LEDYBA]: EggTier.COMMON,
[Species.SPINARAK]: EggTier.COMMON, [Species.SPINARAK]: EggTier.COMMON,
[Species.CHINCHOU]: EggTier.COMMON, [Species.CHINCHOU]: EggTier.COMMON,
[Species.PICHU]: EggTier.COMMON, [Species.PICHU]: EggTier.RARE,
[Species.CLEFFA]: EggTier.COMMON, [Species.CLEFFA]: EggTier.COMMON,
[Species.IGGLYBUFF]: EggTier.COMMON, [Species.IGGLYBUFF]: EggTier.COMMON,
[Species.TOGEPI]: EggTier.COMMON, [Species.TOGEPI]: EggTier.COMMON,
[Species.NATU]: EggTier.COMMON, [Species.NATU]: EggTier.COMMON,
[Species.MAREEP]: EggTier.COMMON, [Species.MAREEP]: EggTier.COMMON,
[Species.MARILL]: EggTier.RARE,
[Species.SUDOWOODO]: EggTier.COMMON,
[Species.HOPPIP]: EggTier.COMMON, [Species.HOPPIP]: EggTier.COMMON,
[Species.AIPOM]: EggTier.COMMON, [Species.AIPOM]: EggTier.COMMON,
[Species.SUNKERN]: EggTier.COMMON, [Species.SUNKERN]: EggTier.COMMON,
@ -109,7 +96,6 @@ export const speciesEggTiers = {
[Species.MURKROW]: EggTier.COMMON, [Species.MURKROW]: EggTier.COMMON,
[Species.MISDREAVUS]: EggTier.COMMON, [Species.MISDREAVUS]: EggTier.COMMON,
[Species.UNOWN]: EggTier.COMMON, [Species.UNOWN]: EggTier.COMMON,
[Species.WOBBUFFET]: EggTier.COMMON,
[Species.GIRAFARIG]: EggTier.COMMON, [Species.GIRAFARIG]: EggTier.COMMON,
[Species.PINECO]: EggTier.COMMON, [Species.PINECO]: EggTier.COMMON,
[Species.DUNSPARCE]: EggTier.COMMON, [Species.DUNSPARCE]: EggTier.COMMON,
@ -125,7 +111,6 @@ export const speciesEggTiers = {
[Species.CORSOLA]: EggTier.COMMON, [Species.CORSOLA]: EggTier.COMMON,
[Species.REMORAID]: EggTier.COMMON, [Species.REMORAID]: EggTier.COMMON,
[Species.DELIBIRD]: EggTier.COMMON, [Species.DELIBIRD]: EggTier.COMMON,
[Species.MANTINE]: EggTier.COMMON,
[Species.SKARMORY]: EggTier.RARE, [Species.SKARMORY]: EggTier.RARE,
[Species.HOUNDOUR]: EggTier.COMMON, [Species.HOUNDOUR]: EggTier.COMMON,
[Species.PHANPY]: EggTier.COMMON, [Species.PHANPY]: EggTier.COMMON,
@ -145,7 +130,7 @@ export const speciesEggTiers = {
[Species.CELEBI]: EggTier.EPIC, [Species.CELEBI]: EggTier.EPIC,
[Species.TREECKO]: EggTier.COMMON, [Species.TREECKO]: EggTier.COMMON,
[Species.TORCHIC]: EggTier.RARE, [Species.TORCHIC]: EggTier.COMMON,
[Species.MUDKIP]: EggTier.COMMON, [Species.MUDKIP]: EggTier.COMMON,
[Species.POOCHYENA]: EggTier.COMMON, [Species.POOCHYENA]: EggTier.COMMON,
[Species.ZIGZAGOON]: EggTier.COMMON, [Species.ZIGZAGOON]: EggTier.COMMON,
@ -154,14 +139,14 @@ export const speciesEggTiers = {
[Species.SEEDOT]: EggTier.COMMON, [Species.SEEDOT]: EggTier.COMMON,
[Species.TAILLOW]: EggTier.COMMON, [Species.TAILLOW]: EggTier.COMMON,
[Species.WINGULL]: EggTier.COMMON, [Species.WINGULL]: EggTier.COMMON,
[Species.RALTS]: EggTier.COMMON, [Species.RALTS]: EggTier.RARE,
[Species.SURSKIT]: EggTier.COMMON, [Species.SURSKIT]: EggTier.COMMON,
[Species.SHROOMISH]: EggTier.COMMON, [Species.SHROOMISH]: EggTier.COMMON,
[Species.SLAKOTH]: EggTier.RARE, [Species.SLAKOTH]: EggTier.RARE,
[Species.NINCADA]: EggTier.RARE, [Species.NINCADA]: EggTier.RARE,
[Species.WHISMUR]: EggTier.COMMON, [Species.WHISMUR]: EggTier.COMMON,
[Species.MAKUHITA]: EggTier.COMMON, [Species.MAKUHITA]: EggTier.COMMON,
[Species.AZURILL]: EggTier.RARE, [Species.AZURILL]: EggTier.COMMON,
[Species.NOSEPASS]: EggTier.COMMON, [Species.NOSEPASS]: EggTier.COMMON,
[Species.SKITTY]: EggTier.COMMON, [Species.SKITTY]: EggTier.COMMON,
[Species.SABLEYE]: EggTier.COMMON, [Species.SABLEYE]: EggTier.COMMON,
@ -173,7 +158,6 @@ export const speciesEggTiers = {
[Species.MINUN]: EggTier.COMMON, [Species.MINUN]: EggTier.COMMON,
[Species.VOLBEAT]: EggTier.COMMON, [Species.VOLBEAT]: EggTier.COMMON,
[Species.ILLUMISE]: EggTier.COMMON, [Species.ILLUMISE]: EggTier.COMMON,
[Species.ROSELIA]: EggTier.COMMON,
[Species.GULPIN]: EggTier.COMMON, [Species.GULPIN]: EggTier.COMMON,
[Species.CARVANHA]: EggTier.COMMON, [Species.CARVANHA]: EggTier.COMMON,
[Species.WAILMER]: EggTier.COMMON, [Species.WAILMER]: EggTier.COMMON,
@ -191,21 +175,20 @@ export const speciesEggTiers = {
[Species.BARBOACH]: EggTier.COMMON, [Species.BARBOACH]: EggTier.COMMON,
[Species.CORPHISH]: EggTier.COMMON, [Species.CORPHISH]: EggTier.COMMON,
[Species.BALTOY]: EggTier.COMMON, [Species.BALTOY]: EggTier.COMMON,
[Species.LILEEP]: EggTier.COMMON, [Species.LILEEP]: EggTier.RARE,
[Species.ANORITH]: EggTier.COMMON, [Species.ANORITH]: EggTier.RARE,
[Species.FEEBAS]: EggTier.RARE, [Species.FEEBAS]: EggTier.RARE,
[Species.CASTFORM]: EggTier.COMMON, [Species.CASTFORM]: EggTier.COMMON,
[Species.KECLEON]: EggTier.COMMON, [Species.KECLEON]: EggTier.COMMON,
[Species.SHUPPET]: EggTier.COMMON, [Species.SHUPPET]: EggTier.COMMON,
[Species.DUSKULL]: EggTier.COMMON, [Species.DUSKULL]: EggTier.COMMON,
[Species.TROPIUS]: EggTier.COMMON, [Species.TROPIUS]: EggTier.COMMON,
[Species.CHIMECHO]: EggTier.COMMON,
[Species.ABSOL]: EggTier.RARE, [Species.ABSOL]: EggTier.RARE,
[Species.WYNAUT]: EggTier.COMMON, [Species.WYNAUT]: EggTier.COMMON,
[Species.SNORUNT]: EggTier.COMMON, [Species.SNORUNT]: EggTier.COMMON,
[Species.SPHEAL]: EggTier.COMMON, [Species.SPHEAL]: EggTier.COMMON,
[Species.CLAMPERL]: EggTier.COMMON, [Species.CLAMPERL]: EggTier.COMMON,
[Species.RELICANTH]: EggTier.COMMON, [Species.RELICANTH]: EggTier.RARE,
[Species.LUVDISC]: EggTier.COMMON, [Species.LUVDISC]: EggTier.COMMON,
[Species.BAGON]: EggTier.RARE, [Species.BAGON]: EggTier.RARE,
[Species.BELDUM]: EggTier.RARE, [Species.BELDUM]: EggTier.RARE,
@ -228,8 +211,8 @@ export const speciesEggTiers = {
[Species.KRICKETOT]: EggTier.COMMON, [Species.KRICKETOT]: EggTier.COMMON,
[Species.SHINX]: EggTier.COMMON, [Species.SHINX]: EggTier.COMMON,
[Species.BUDEW]: EggTier.COMMON, [Species.BUDEW]: EggTier.COMMON,
[Species.CRANIDOS]: EggTier.COMMON, [Species.CRANIDOS]: EggTier.RARE,
[Species.SHIELDON]: EggTier.COMMON, [Species.SHIELDON]: EggTier.RARE,
[Species.BURMY]: EggTier.COMMON, [Species.BURMY]: EggTier.COMMON,
[Species.COMBEE]: EggTier.COMMON, [Species.COMBEE]: EggTier.COMMON,
[Species.PACHIRISU]: EggTier.COMMON, [Species.PACHIRISU]: EggTier.COMMON,
@ -244,12 +227,12 @@ export const speciesEggTiers = {
[Species.BRONZOR]: EggTier.COMMON, [Species.BRONZOR]: EggTier.COMMON,
[Species.BONSLY]: EggTier.COMMON, [Species.BONSLY]: EggTier.COMMON,
[Species.MIME_JR]: EggTier.COMMON, [Species.MIME_JR]: EggTier.COMMON,
[Species.HAPPINY]: EggTier.COMMON, [Species.HAPPINY]: EggTier.RARE,
[Species.CHATOT]: EggTier.COMMON, [Species.CHATOT]: EggTier.COMMON,
[Species.SPIRITOMB]: EggTier.RARE, [Species.SPIRITOMB]: EggTier.RARE,
[Species.GIBLE]: EggTier.RARE, [Species.GIBLE]: EggTier.RARE,
[Species.MUNCHLAX]: EggTier.RARE, [Species.MUNCHLAX]: EggTier.RARE,
[Species.RIOLU]: EggTier.COMMON, [Species.RIOLU]: EggTier.RARE,
[Species.HIPPOPOTAS]: EggTier.COMMON, [Species.HIPPOPOTAS]: EggTier.COMMON,
[Species.SKORUPI]: EggTier.COMMON, [Species.SKORUPI]: EggTier.COMMON,
[Species.CROAGUNK]: EggTier.COMMON, [Species.CROAGUNK]: EggTier.COMMON,
@ -264,10 +247,10 @@ export const speciesEggTiers = {
[Species.DIALGA]: EggTier.LEGENDARY, [Species.DIALGA]: EggTier.LEGENDARY,
[Species.PALKIA]: EggTier.LEGENDARY, [Species.PALKIA]: EggTier.LEGENDARY,
[Species.HEATRAN]: EggTier.EPIC, [Species.HEATRAN]: EggTier.EPIC,
[Species.REGIGIGAS]: EggTier.EPIC, [Species.REGIGIGAS]: EggTier.LEGENDARY,
[Species.GIRATINA]: EggTier.LEGENDARY, [Species.GIRATINA]: EggTier.LEGENDARY,
[Species.CRESSELIA]: EggTier.EPIC, [Species.CRESSELIA]: EggTier.EPIC,
[Species.PHIONE]: EggTier.RARE, [Species.PHIONE]: EggTier.EPIC,
[Species.MANAPHY]: EggTier.EPIC, [Species.MANAPHY]: EggTier.EPIC,
[Species.DARKRAI]: EggTier.EPIC, [Species.DARKRAI]: EggTier.EPIC,
[Species.SHAYMIN]: EggTier.EPIC, [Species.SHAYMIN]: EggTier.EPIC,
@ -289,7 +272,7 @@ export const speciesEggTiers = {
[Species.ROGGENROLA]: EggTier.COMMON, [Species.ROGGENROLA]: EggTier.COMMON,
[Species.WOOBAT]: EggTier.COMMON, [Species.WOOBAT]: EggTier.COMMON,
[Species.DRILBUR]: EggTier.RARE, [Species.DRILBUR]: EggTier.RARE,
[Species.AUDINO]: EggTier.COMMON, [Species.AUDINO]: EggTier.RARE,
[Species.TIMBURR]: EggTier.RARE, [Species.TIMBURR]: EggTier.RARE,
[Species.TYMPOLE]: EggTier.COMMON, [Species.TYMPOLE]: EggTier.COMMON,
[Species.THROH]: EggTier.RARE, [Species.THROH]: EggTier.RARE,
@ -306,8 +289,8 @@ export const speciesEggTiers = {
[Species.SCRAGGY]: EggTier.COMMON, [Species.SCRAGGY]: EggTier.COMMON,
[Species.SIGILYPH]: EggTier.RARE, [Species.SIGILYPH]: EggTier.RARE,
[Species.YAMASK]: EggTier.COMMON, [Species.YAMASK]: EggTier.COMMON,
[Species.TIRTOUGA]: EggTier.COMMON, [Species.TIRTOUGA]: EggTier.RARE,
[Species.ARCHEN]: EggTier.COMMON, [Species.ARCHEN]: EggTier.RARE,
[Species.TRUBBISH]: EggTier.COMMON, [Species.TRUBBISH]: EggTier.COMMON,
[Species.ZORUA]: EggTier.COMMON, [Species.ZORUA]: EggTier.COMMON,
[Species.MINCCINO]: EggTier.COMMON, [Species.MINCCINO]: EggTier.COMMON,
@ -339,7 +322,7 @@ export const speciesEggTiers = {
[Species.BOUFFALANT]: EggTier.RARE, [Species.BOUFFALANT]: EggTier.RARE,
[Species.RUFFLET]: EggTier.COMMON, [Species.RUFFLET]: EggTier.COMMON,
[Species.VULLABY]: EggTier.COMMON, [Species.VULLABY]: EggTier.COMMON,
[Species.HEATMOR]: EggTier.COMMON, [Species.HEATMOR]: EggTier.RARE,
[Species.DURANT]: EggTier.RARE, [Species.DURANT]: EggTier.RARE,
[Species.DEINO]: EggTier.RARE, [Species.DEINO]: EggTier.RARE,
[Species.LARVESTA]: EggTier.RARE, [Species.LARVESTA]: EggTier.RARE,
@ -358,7 +341,7 @@ export const speciesEggTiers = {
[Species.CHESPIN]: EggTier.COMMON, [Species.CHESPIN]: EggTier.COMMON,
[Species.FENNEKIN]: EggTier.COMMON, [Species.FENNEKIN]: EggTier.COMMON,
[Species.FROAKIE]: EggTier.RARE, [Species.FROAKIE]: EggTier.COMMON,
[Species.BUNNELBY]: EggTier.COMMON, [Species.BUNNELBY]: EggTier.COMMON,
[Species.FLETCHLING]: EggTier.COMMON, [Species.FLETCHLING]: EggTier.COMMON,
[Species.SCATTERBUG]: EggTier.COMMON, [Species.SCATTERBUG]: EggTier.COMMON,
@ -376,8 +359,8 @@ export const speciesEggTiers = {
[Species.SKRELP]: EggTier.COMMON, [Species.SKRELP]: EggTier.COMMON,
[Species.CLAUNCHER]: EggTier.COMMON, [Species.CLAUNCHER]: EggTier.COMMON,
[Species.HELIOPTILE]: EggTier.COMMON, [Species.HELIOPTILE]: EggTier.COMMON,
[Species.TYRUNT]: EggTier.COMMON, [Species.TYRUNT]: EggTier.RARE,
[Species.AMAURA]: EggTier.COMMON, [Species.AMAURA]: EggTier.RARE,
[Species.HAWLUCHA]: EggTier.RARE, [Species.HAWLUCHA]: EggTier.RARE,
[Species.DEDENNE]: EggTier.COMMON, [Species.DEDENNE]: EggTier.COMMON,
[Species.CARBINK]: EggTier.COMMON, [Species.CARBINK]: EggTier.COMMON,
@ -386,18 +369,18 @@ export const speciesEggTiers = {
[Species.PHANTUMP]: EggTier.COMMON, [Species.PHANTUMP]: EggTier.COMMON,
[Species.PUMPKABOO]: EggTier.COMMON, [Species.PUMPKABOO]: EggTier.COMMON,
[Species.BERGMITE]: EggTier.COMMON, [Species.BERGMITE]: EggTier.COMMON,
[Species.NOIBAT]: EggTier.COMMON, [Species.NOIBAT]: EggTier.RARE,
[Species.XERNEAS]: EggTier.LEGENDARY, [Species.XERNEAS]: EggTier.LEGENDARY,
[Species.YVELTAL]: EggTier.LEGENDARY, [Species.YVELTAL]: EggTier.LEGENDARY,
[Species.ZYGARDE]: EggTier.LEGENDARY, [Species.ZYGARDE]: EggTier.LEGENDARY,
[Species.DIANCIE]: EggTier.EPIC, [Species.DIANCIE]: EggTier.EPIC,
[Species.HOOPA]: EggTier.EPIC, [Species.HOOPA]: EggTier.EPIC,
[Species.VOLCANION]: EggTier.EPIC, [Species.VOLCANION]: EggTier.EPIC,
[Species.ETERNAL_FLOETTE]: EggTier.RARE, [Species.ETERNAL_FLOETTE]: EggTier.EPIC,
[Species.ROWLET]: EggTier.COMMON, [Species.ROWLET]: EggTier.COMMON,
[Species.LITTEN]: EggTier.COMMON, [Species.LITTEN]: EggTier.COMMON,
[Species.POPPLIO]: EggTier.RARE, [Species.POPPLIO]: EggTier.COMMON,
[Species.PIKIPEK]: EggTier.COMMON, [Species.PIKIPEK]: EggTier.COMMON,
[Species.YUNGOOS]: EggTier.COMMON, [Species.YUNGOOS]: EggTier.COMMON,
[Species.GRUBBIN]: EggTier.COMMON, [Species.GRUBBIN]: EggTier.COMMON,
@ -420,7 +403,7 @@ export const speciesEggTiers = {
[Species.WIMPOD]: EggTier.COMMON, [Species.WIMPOD]: EggTier.COMMON,
[Species.SANDYGAST]: EggTier.COMMON, [Species.SANDYGAST]: EggTier.COMMON,
[Species.PYUKUMUKU]: EggTier.COMMON, [Species.PYUKUMUKU]: EggTier.COMMON,
[Species.TYPE_NULL]: EggTier.RARE, [Species.TYPE_NULL]: EggTier.EPIC,
[Species.MINIOR]: EggTier.RARE, [Species.MINIOR]: EggTier.RARE,
[Species.KOMALA]: EggTier.COMMON, [Species.KOMALA]: EggTier.COMMON,
[Species.TURTONATOR]: EggTier.RARE, [Species.TURTONATOR]: EggTier.RARE,
@ -434,7 +417,7 @@ export const speciesEggTiers = {
[Species.TAPU_LELE]: EggTier.EPIC, [Species.TAPU_LELE]: EggTier.EPIC,
[Species.TAPU_BULU]: EggTier.EPIC, [Species.TAPU_BULU]: EggTier.EPIC,
[Species.TAPU_FINI]: EggTier.EPIC, [Species.TAPU_FINI]: EggTier.EPIC,
[Species.COSMOG]: EggTier.EPIC, [Species.COSMOG]: EggTier.LEGENDARY,
[Species.NIHILEGO]: EggTier.EPIC, [Species.NIHILEGO]: EggTier.EPIC,
[Species.BUZZWOLE]: EggTier.EPIC, [Species.BUZZWOLE]: EggTier.EPIC,
[Species.PHEROMOSA]: EggTier.EPIC, [Species.PHEROMOSA]: EggTier.EPIC,
@ -451,15 +434,15 @@ export const speciesEggTiers = {
[Species.ZERAORA]: EggTier.EPIC, [Species.ZERAORA]: EggTier.EPIC,
[Species.MELTAN]: EggTier.EPIC, [Species.MELTAN]: EggTier.EPIC,
[Species.ALOLA_RATTATA]: EggTier.COMMON, [Species.ALOLA_RATTATA]: EggTier.COMMON,
[Species.ALOLA_SANDSHREW]: EggTier.COMMON, [Species.ALOLA_SANDSHREW]: EggTier.RARE,
[Species.ALOLA_VULPIX]: EggTier.COMMON, [Species.ALOLA_VULPIX]: EggTier.RARE,
[Species.ALOLA_DIGLETT]: EggTier.COMMON, [Species.ALOLA_DIGLETT]: EggTier.RARE,
[Species.ALOLA_MEOWTH]: EggTier.COMMON, [Species.ALOLA_MEOWTH]: EggTier.RARE,
[Species.ALOLA_GEODUDE]: EggTier.COMMON, [Species.ALOLA_GEODUDE]: EggTier.RARE,
[Species.ALOLA_GRIMER]: EggTier.COMMON, [Species.ALOLA_GRIMER]: EggTier.RARE,
[Species.GROOKEY]: EggTier.COMMON, [Species.GROOKEY]: EggTier.COMMON,
[Species.SCORBUNNY]: EggTier.RARE, [Species.SCORBUNNY]: EggTier.COMMON,
[Species.SOBBLE]: EggTier.COMMON, [Species.SOBBLE]: EggTier.COMMON,
[Species.SKWOVET]: EggTier.COMMON, [Species.SKWOVET]: EggTier.COMMON,
[Species.ROOKIDEE]: EggTier.COMMON, [Species.ROOKIDEE]: EggTier.COMMON,
@ -505,29 +488,28 @@ export const speciesEggTiers = {
[Species.GLASTRIER]: EggTier.EPIC, [Species.GLASTRIER]: EggTier.EPIC,
[Species.SPECTRIER]: EggTier.EPIC, [Species.SPECTRIER]: EggTier.EPIC,
[Species.CALYREX]: EggTier.LEGENDARY, [Species.CALYREX]: EggTier.LEGENDARY,
[Species.GALAR_MEOWTH]: EggTier.COMMON, [Species.ENAMORUS]: EggTier.EPIC,
[Species.GALAR_PONYTA]: EggTier.COMMON, [Species.GALAR_MEOWTH]: EggTier.RARE,
[Species.GALAR_SLOWPOKE]: EggTier.COMMON, [Species.GALAR_PONYTA]: EggTier.RARE,
[Species.GALAR_FARFETCHD]: EggTier.COMMON, [Species.GALAR_SLOWPOKE]: EggTier.RARE,
[Species.GALAR_CORSOLA]: EggTier.COMMON, [Species.GALAR_FARFETCHD]: EggTier.RARE,
[Species.GALAR_ZIGZAGOON]: EggTier.COMMON,
[Species.GALAR_DARUMAKA]: EggTier.RARE,
[Species.GALAR_YAMASK]: EggTier.COMMON,
[Species.GALAR_STUNFISK]: EggTier.COMMON,
[Species.GALAR_MR_MIME]: EggTier.COMMON,
[Species.GALAR_ARTICUNO]: EggTier.EPIC, [Species.GALAR_ARTICUNO]: EggTier.EPIC,
[Species.GALAR_ZAPDOS]: EggTier.EPIC, [Species.GALAR_ZAPDOS]: EggTier.EPIC,
[Species.GALAR_MOLTRES]: EggTier.EPIC, [Species.GALAR_MOLTRES]: EggTier.EPIC,
[Species.GALAR_CORSOLA]: EggTier.RARE,
[Species.GALAR_ZIGZAGOON]: EggTier.RARE,
[Species.GALAR_DARUMAKA]: EggTier.RARE,
[Species.GALAR_YAMASK]: EggTier.RARE,
[Species.GALAR_STUNFISK]: EggTier.RARE,
[Species.HISUI_GROWLITHE]: EggTier.RARE, [Species.HISUI_GROWLITHE]: EggTier.RARE,
[Species.HISUI_VOLTORB]: EggTier.COMMON, [Species.HISUI_VOLTORB]: EggTier.RARE,
[Species.HISUI_QWILFISH]: EggTier.RARE, [Species.HISUI_QWILFISH]: EggTier.RARE,
[Species.HISUI_SNEASEL]: EggTier.RARE, [Species.HISUI_SNEASEL]: EggTier.RARE,
[Species.HISUI_ZORUA]: EggTier.COMMON, [Species.HISUI_ZORUA]: EggTier.RARE,
[Species.ENAMORUS]: EggTier.EPIC,
[Species.SPRIGATITO]: EggTier.RARE, [Species.SPRIGATITO]: EggTier.COMMON,
[Species.FUECOCO]: EggTier.RARE, [Species.FUECOCO]: EggTier.COMMON,
[Species.QUAXLY]: EggTier.RARE, [Species.QUAXLY]: EggTier.COMMON,
[Species.LECHONK]: EggTier.COMMON, [Species.LECHONK]: EggTier.COMMON,
[Species.TAROUNTULA]: EggTier.COMMON, [Species.TAROUNTULA]: EggTier.COMMON,
[Species.NYMBLE]: EggTier.COMMON, [Species.NYMBLE]: EggTier.COMMON,
@ -551,7 +533,7 @@ export const speciesEggTiers = {
[Species.TINKATINK]: EggTier.RARE, [Species.TINKATINK]: EggTier.RARE,
[Species.WIGLETT]: EggTier.COMMON, [Species.WIGLETT]: EggTier.COMMON,
[Species.BOMBIRDIER]: EggTier.COMMON, [Species.BOMBIRDIER]: EggTier.COMMON,
[Species.FINIZEN]: EggTier.COMMON, [Species.FINIZEN]: EggTier.RARE,
[Species.VAROOM]: EggTier.RARE, [Species.VAROOM]: EggTier.RARE,
[Species.CYCLIZAR]: EggTier.RARE, [Species.CYCLIZAR]: EggTier.RARE,
[Species.ORTHWORM]: EggTier.RARE, [Species.ORTHWORM]: EggTier.RARE,
@ -598,6 +580,6 @@ export const speciesEggTiers = {
[Species.TERAPAGOS]: EggTier.LEGENDARY, [Species.TERAPAGOS]: EggTier.LEGENDARY,
[Species.PECHARUNT]: EggTier.EPIC, [Species.PECHARUNT]: EggTier.EPIC,
[Species.PALDEA_TAUROS]: EggTier.RARE, [Species.PALDEA_TAUROS]: EggTier.RARE,
[Species.PALDEA_WOOPER]: EggTier.COMMON, [Species.PALDEA_WOOPER]: EggTier.RARE,
[Species.BLOODMOON_URSALUNA]: EggTier.EPIC, [Species.BLOODMOON_URSALUNA]: EggTier.EPIC
}; };

View File

@ -3,10 +3,10 @@ import { Species } from "#enums/species";
export const POKERUS_STARTER_COUNT = 5; export const POKERUS_STARTER_COUNT = 5;
// #region Friendship constants // #region Friendship constants
export const CLASSIC_CANDY_FRIENDSHIP_MULTIPLIER = 2; export const CLASSIC_CANDY_FRIENDSHIP_MULTIPLIER = 3;
export const FRIENDSHIP_GAIN_FROM_BATTLE = 2; export const FRIENDSHIP_GAIN_FROM_BATTLE = 4;
export const FRIENDSHIP_GAIN_FROM_RARE_CANDY = 5; export const FRIENDSHIP_GAIN_FROM_RARE_CANDY = 6;
export const FRIENDSHIP_LOSS_FROM_FAINT = 10; export const FRIENDSHIP_LOSS_FROM_FAINT = 5;
/** /**
* Function to get the cumulative friendship threshold at which a candy is earned * Function to get the cumulative friendship threshold at which a candy is earned
@ -16,19 +16,19 @@ export const FRIENDSHIP_LOSS_FROM_FAINT = 10;
export function getStarterValueFriendshipCap(starterCost: number): number { export function getStarterValueFriendshipCap(starterCost: number): number {
switch (starterCost) { switch (starterCost) {
case 1: case 1:
return 20; return 25;
case 2: case 2:
return 40; return 50;
case 3: case 3:
return 60; return 75;
case 4: case 4:
return 100; return 100;
case 5: case 5:
return 140; return 150;
case 6: case 6:
return 200; return 200;
case 7: case 7:
return 280; return 300;
case 8: case 8:
case 9: case 9:
return 450; return 450;
@ -47,7 +47,7 @@ export const speciesStarterCosts = {
[Species.RATTATA]: 1, [Species.RATTATA]: 1,
[Species.SPEAROW]: 1, [Species.SPEAROW]: 1,
[Species.EKANS]: 2, [Species.EKANS]: 2,
[Species.PIKACHU]: 3, [Species.PIKACHU]: 4,
[Species.SANDSHREW]: 2, [Species.SANDSHREW]: 2,
[Species.NIDORAN_F]: 3, [Species.NIDORAN_F]: 3,
[Species.NIDORAN_M]: 3, [Species.NIDORAN_M]: 3,
@ -88,7 +88,7 @@ export const speciesStarterCosts = {
[Species.HITMONCHAN]: 4, [Species.HITMONCHAN]: 4,
[Species.LICKITUNG]: 3, [Species.LICKITUNG]: 3,
[Species.KOFFING]: 2, [Species.KOFFING]: 2,
[Species.RHYHORN]: 3, [Species.RHYHORN]: 4,
[Species.CHANSEY]: 3, [Species.CHANSEY]: 3,
[Species.TANGELA]: 3, [Species.TANGELA]: 3,
[Species.KANGASKHAN]: 4, [Species.KANGASKHAN]: 4,
@ -111,12 +111,12 @@ export const speciesStarterCosts = {
[Species.KABUTO]: 3, [Species.KABUTO]: 3,
[Species.AERODACTYL]: 5, [Species.AERODACTYL]: 5,
[Species.SNORLAX]: 5, [Species.SNORLAX]: 5,
[Species.ARTICUNO]: 6, [Species.ARTICUNO]: 5,
[Species.ZAPDOS]: 6, [Species.ZAPDOS]: 6,
[Species.MOLTRES]: 6, [Species.MOLTRES]: 6,
[Species.DRATINI]: 4, [Species.DRATINI]: 4,
[Species.MEWTWO]: 8, [Species.MEWTWO]: 8,
[Species.MEW]: 6, [Species.MEW]: 5,
[Species.CHIKORITA]: 2, [Species.CHIKORITA]: 2,
[Species.CYNDAQUIL]: 3, [Species.CYNDAQUIL]: 3,
@ -126,7 +126,7 @@ export const speciesStarterCosts = {
[Species.LEDYBA]: 1, [Species.LEDYBA]: 1,
[Species.SPINARAK]: 1, [Species.SPINARAK]: 1,
[Species.CHINCHOU]: 2, [Species.CHINCHOU]: 2,
[Species.PICHU]: 2, [Species.PICHU]: 4,
[Species.CLEFFA]: 2, [Species.CLEFFA]: 2,
[Species.IGGLYBUFF]: 1, [Species.IGGLYBUFF]: 1,
[Species.TOGEPI]: 3, [Species.TOGEPI]: 3,
@ -175,7 +175,7 @@ export const speciesStarterCosts = {
[Species.LARVITAR]: 4, [Species.LARVITAR]: 4,
[Species.LUGIA]: 8, [Species.LUGIA]: 8,
[Species.HO_OH]: 8, [Species.HO_OH]: 8,
[Species.CELEBI]: 6, [Species.CELEBI]: 5,
[Species.TREECKO]: 3, [Species.TREECKO]: 3,
[Species.TORCHIC]: 4, [Species.TORCHIC]: 4,
@ -187,7 +187,7 @@ export const speciesStarterCosts = {
[Species.SEEDOT]: 2, [Species.SEEDOT]: 2,
[Species.TAILLOW]: 3, [Species.TAILLOW]: 3,
[Species.WINGULL]: 2, [Species.WINGULL]: 2,
[Species.RALTS]: 3, [Species.RALTS]: 4,
[Species.SURSKIT]: 2, [Species.SURSKIT]: 2,
[Species.SHROOMISH]: 3, [Species.SHROOMISH]: 3,
[Species.SLAKOTH]: 4, [Species.SLAKOTH]: 4,
@ -198,7 +198,7 @@ export const speciesStarterCosts = {
[Species.NOSEPASS]: 2, [Species.NOSEPASS]: 2,
[Species.SKITTY]: 1, [Species.SKITTY]: 1,
[Species.SABLEYE]: 2, [Species.SABLEYE]: 2,
[Species.MAWILE]: 3, [Species.MAWILE]: 2,
[Species.ARON]: 3, [Species.ARON]: 3,
[Species.MEDITITE]: 3, [Species.MEDITITE]: 3,
[Species.ELECTRIKE]: 2, [Species.ELECTRIKE]: 2,
@ -243,7 +243,7 @@ export const speciesStarterCosts = {
[Species.BAGON]: 4, [Species.BAGON]: 4,
[Species.BELDUM]: 4, [Species.BELDUM]: 4,
[Species.REGIROCK]: 6, [Species.REGIROCK]: 6,
[Species.REGICE]: 6, [Species.REGICE]: 5,
[Species.REGISTEEL]: 6, [Species.REGISTEEL]: 6,
[Species.LATIAS]: 7, [Species.LATIAS]: 7,
[Species.LATIOS]: 7, [Species.LATIOS]: 7,
@ -291,19 +291,19 @@ export const speciesStarterCosts = {
[Species.MANTYKE]: 2, [Species.MANTYKE]: 2,
[Species.SNOVER]: 2, [Species.SNOVER]: 2,
[Species.ROTOM]: 5, [Species.ROTOM]: 5,
[Species.UXIE]: 6, [Species.UXIE]: 5,
[Species.MESPRIT]: 6, [Species.MESPRIT]: 5,
[Species.AZELF]: 6, [Species.AZELF]: 6,
[Species.DIALGA]: 8, [Species.DIALGA]: 8,
[Species.PALKIA]: 8, [Species.PALKIA]: 8,
[Species.HEATRAN]: 6, [Species.HEATRAN]: 7,
[Species.REGIGIGAS]: 7, [Species.REGIGIGAS]: 7,
[Species.GIRATINA]: 8, [Species.GIRATINA]: 8,
[Species.CRESSELIA]: 6, [Species.CRESSELIA]: 6,
[Species.PHIONE]: 4, [Species.PHIONE]: 4,
[Species.MANAPHY]: 7, [Species.MANAPHY]: 7,
[Species.DARKRAI]: 7, [Species.DARKRAI]: 7,
[Species.SHAYMIN]: 6, [Species.SHAYMIN]: 5,
[Species.ARCEUS]: 9, [Species.ARCEUS]: 9,
[Species.VICTINI]: 7, [Species.VICTINI]: 7,
@ -351,7 +351,7 @@ export const speciesStarterCosts = {
[Species.DEERLING]: 2, [Species.DEERLING]: 2,
[Species.EMOLGA]: 2, [Species.EMOLGA]: 2,
[Species.KARRABLAST]: 3, [Species.KARRABLAST]: 3,
[Species.FOONGUS]: 2, [Species.FOONGUS]: 3,
[Species.FRILLISH]: 3, [Species.FRILLISH]: 3,
[Species.ALOMOMOLA]: 4, [Species.ALOMOMOLA]: 4,
[Species.JOLTIK]: 3, [Species.JOLTIK]: 3,
@ -410,7 +410,7 @@ export const speciesStarterCosts = {
[Species.CLAUNCHER]: 3, [Species.CLAUNCHER]: 3,
[Species.HELIOPTILE]: 3, [Species.HELIOPTILE]: 3,
[Species.TYRUNT]: 3, [Species.TYRUNT]: 3,
[Species.AMAURA]: 3, [Species.AMAURA]: 2,
[Species.HAWLUCHA]: 4, [Species.HAWLUCHA]: 4,
[Species.DEDENNE]: 2, [Species.DEDENNE]: 2,
[Species.CARBINK]: 2, [Species.CARBINK]: 2,
@ -425,7 +425,7 @@ export const speciesStarterCosts = {
[Species.ZYGARDE]: 8, [Species.ZYGARDE]: 8,
[Species.DIANCIE]: 7, [Species.DIANCIE]: 7,
[Species.HOOPA]: 7, [Species.HOOPA]: 7,
[Species.VOLCANION]: 6, [Species.VOLCANION]: 7,
[Species.ETERNAL_FLOETTE]: 4, [Species.ETERNAL_FLOETTE]: 4,
[Species.ROWLET]: 3, [Species.ROWLET]: 3,
@ -464,21 +464,21 @@ export const speciesStarterCosts = {
[Species.DHELMISE]: 4, [Species.DHELMISE]: 4,
[Species.JANGMO_O]: 4, [Species.JANGMO_O]: 4,
[Species.TAPU_KOKO]: 6, [Species.TAPU_KOKO]: 6,
[Species.TAPU_LELE]: 6, [Species.TAPU_LELE]: 7,
[Species.TAPU_BULU]: 6, [Species.TAPU_BULU]: 6,
[Species.TAPU_FINI]: 6, [Species.TAPU_FINI]: 5,
[Species.COSMOG]: 7, [Species.COSMOG]: 7,
[Species.NIHILEGO]: 6, [Species.NIHILEGO]: 6,
[Species.BUZZWOLE]: 6, [Species.BUZZWOLE]: 6,
[Species.PHEROMOSA]: 7, [Species.PHEROMOSA]: 7,
[Species.XURKITREE]: 6, [Species.XURKITREE]: 6,
[Species.CELESTEELA]: 6, [Species.CELESTEELA]: 6,
[Species.KARTANA]: 7, [Species.KARTANA]: 8,
[Species.GUZZLORD]: 6, [Species.GUZZLORD]: 6,
[Species.NECROZMA]: 8, [Species.NECROZMA]: 8,
[Species.MAGEARNA]: 7, [Species.MAGEARNA]: 7,
[Species.MARSHADOW]: 7, [Species.MARSHADOW]: 7,
[Species.POIPOLE]: 7, [Species.POIPOLE]: 8,
[Species.STAKATAKA]: 6, [Species.STAKATAKA]: 6,
[Species.BLACEPHALON]: 7, [Species.BLACEPHALON]: 7,
[Species.ZERAORA]: 6, [Species.ZERAORA]: 6,
@ -532,31 +532,31 @@ export const speciesStarterCosts = {
[Species.ZAMAZENTA]: 8, [Species.ZAMAZENTA]: 8,
[Species.ETERNATUS]: 10, [Species.ETERNATUS]: 10,
[Species.KUBFU]: 6, [Species.KUBFU]: 6,
[Species.ZARUDE]: 6, [Species.ZARUDE]: 5,
[Species.REGIELEKI]: 6, [Species.REGIELEKI]: 6,
[Species.REGIDRAGO]: 6, [Species.REGIDRAGO]: 6,
[Species.GLASTRIER]: 6, [Species.GLASTRIER]: 6,
[Species.SPECTRIER]: 7, [Species.SPECTRIER]: 8,
[Species.CALYREX]: 8, [Species.CALYREX]: 8,
[Species.ENAMORUS]: 7,
[Species.GALAR_MEOWTH]: 3, [Species.GALAR_MEOWTH]: 3,
[Species.GALAR_PONYTA]: 2, [Species.GALAR_PONYTA]: 2,
[Species.GALAR_SLOWPOKE]: 3, [Species.GALAR_SLOWPOKE]: 3,
[Species.GALAR_FARFETCHD]: 3, [Species.GALAR_FARFETCHD]: 3,
[Species.GALAR_MR_MIME]: 3,
[Species.GALAR_ARTICUNO]: 6,
[Species.GALAR_ZAPDOS]: 6,
[Species.GALAR_MOLTRES]: 6,
[Species.GALAR_CORSOLA]: 3, [Species.GALAR_CORSOLA]: 3,
[Species.GALAR_ZIGZAGOON]: 3, [Species.GALAR_ZIGZAGOON]: 3,
[Species.GALAR_DARUMAKA]: 4, [Species.GALAR_DARUMAKA]: 4,
[Species.GALAR_YAMASK]: 3, [Species.GALAR_YAMASK]: 3,
[Species.GALAR_STUNFISK]: 2, [Species.GALAR_STUNFISK]: 2,
[Species.GALAR_MR_MIME]: 3,
[Species.GALAR_ARTICUNO]: 6,
[Species.GALAR_ZAPDOS]: 6,
[Species.GALAR_MOLTRES]: 6,
[Species.HISUI_GROWLITHE]: 4, [Species.HISUI_GROWLITHE]: 4,
[Species.HISUI_VOLTORB]: 3, [Species.HISUI_VOLTORB]: 3,
[Species.HISUI_QWILFISH]: 4, [Species.HISUI_QWILFISH]: 4,
[Species.HISUI_SNEASEL]: 5, [Species.HISUI_SNEASEL]: 5,
[Species.HISUI_ZORUA]: 3, [Species.HISUI_ZORUA]: 3,
[Species.ENAMORUS]: 7,
[Species.SPRIGATITO]: 4, [Species.SPRIGATITO]: 4,
[Species.FUECOCO]: 4, [Species.FUECOCO]: 4,
@ -595,9 +595,9 @@ export const speciesStarterCosts = {
[Species.VELUZA]: 4, [Species.VELUZA]: 4,
[Species.DONDOZO]: 4, [Species.DONDOZO]: 4,
[Species.TATSUGIRI]: 4, [Species.TATSUGIRI]: 4,
[Species.GREAT_TUSK]: 6, [Species.GREAT_TUSK]: 7,
[Species.SCREAM_TAIL]: 6, [Species.SCREAM_TAIL]: 5,
[Species.BRUTE_BONNET]: 6, [Species.BRUTE_BONNET]: 5,
[Species.FLUTTER_MANE]: 7, [Species.FLUTTER_MANE]: 7,
[Species.SLITHER_WING]: 6, [Species.SLITHER_WING]: 6,
[Species.SANDY_SHOCKS]: 6, [Species.SANDY_SHOCKS]: 6,
@ -606,33 +606,33 @@ export const speciesStarterCosts = {
[Species.IRON_HANDS]: 6, [Species.IRON_HANDS]: 6,
[Species.IRON_JUGULIS]: 6, [Species.IRON_JUGULIS]: 6,
[Species.IRON_MOTH]: 6, [Species.IRON_MOTH]: 6,
[Species.IRON_THORNS]: 6, [Species.IRON_THORNS]: 5,
[Species.FRIGIBAX]: 4, [Species.FRIGIBAX]: 4,
[Species.GIMMIGHOUL]: 4, [Species.GIMMIGHOUL]: 4,
[Species.WO_CHIEN]: 6, [Species.WO_CHIEN]: 5,
[Species.CHIEN_PAO]: 7, [Species.CHIEN_PAO]: 7,
[Species.TING_LU]: 6, [Species.TING_LU]: 6,
[Species.CHI_YU]: 7, [Species.CHI_YU]: 7,
[Species.ROARING_MOON]: 6, [Species.ROARING_MOON]: 7,
[Species.IRON_VALIANT]: 6, [Species.IRON_VALIANT]: 6,
[Species.KORAIDON]: 9, [Species.KORAIDON]: 9,
[Species.MIRAIDON]: 9, [Species.MIRAIDON]: 9,
[Species.WALKING_WAKE]: 6, [Species.WALKING_WAKE]: 7,
[Species.IRON_LEAVES]: 6, [Species.IRON_LEAVES]: 6,
[Species.POLTCHAGEIST]: 4, [Species.POLTCHAGEIST]: 4,
[Species.OKIDOGI]: 6, [Species.OKIDOGI]: 6,
[Species.MUNKIDORI]: 6, [Species.MUNKIDORI]: 6,
[Species.FEZANDIPITI]: 6, [Species.FEZANDIPITI]: 5,
[Species.OGERPON]: 7, [Species.OGERPON]: 7,
[Species.GOUGING_FIRE]: 7, [Species.GOUGING_FIRE]: 7,
[Species.RAGING_BOLT]: 6, [Species.RAGING_BOLT]: 7,
[Species.IRON_BOULDER]: 7, [Species.IRON_BOULDER]: 7,
[Species.IRON_CROWN]: 6, [Species.IRON_CROWN]: 7,
[Species.TERAPAGOS]: 8, [Species.TERAPAGOS]: 8,
[Species.PECHARUNT]: 6, [Species.PECHARUNT]: 6,
[Species.PALDEA_TAUROS]: 5, [Species.PALDEA_TAUROS]: 5,
[Species.PALDEA_WOOPER]: 3, [Species.PALDEA_WOOPER]: 3,
[Species.BLOODMOON_URSALUNA]: 6, [Species.BLOODMOON_URSALUNA]: 5,
}; };
const starterCandyCosts: { passive: number; costReduction: [number, number]; egg: number; }[] = [ const starterCandyCosts: { passive: number; costReduction: [number, number]; egg: number; }[] = [

View File

@ -67148,6 +67148,7 @@ export const tmSpecies: TmSpecies = {
Species.VELUZA, Species.VELUZA,
Species.DONDOZO, Species.DONDOZO,
Species.TATSUGIRI, Species.TATSUGIRI,
Species.ANNIHILAPE,
Species.CLODSIRE, Species.CLODSIRE,
Species.FARIGIRAF, Species.FARIGIRAF,
Species.DUDUNSPARCE, Species.DUDUNSPARCE,

View File

@ -90,6 +90,7 @@ export enum CommonAnim {
RAGING_BULL_FIRE, RAGING_BULL_FIRE,
RAGING_BULL_WATER, RAGING_BULL_WATER,
SALT_CURE, SALT_CURE,
POWDER,
SUNNY = 2100, SUNNY = 2100,
RAIN, RAIN,
SANDSTORM, SANDSTORM,

View File

@ -856,6 +856,59 @@ export class SeedTag extends BattlerTag {
} }
} }
/**
* BattlerTag representing the effects of {@link https://bulbapedia.bulbagarden.net/wiki/Powder_(move) | Powder}.
* When the afflicted Pokemon uses a Fire-type move, the move is cancelled, and the
* Pokemon takes damage equal to 1/4 of it's maximum HP (rounded down).
*/
export class PowderTag extends BattlerTag {
constructor() {
super(BattlerTagType.POWDER, [ BattlerTagLapseType.PRE_MOVE, BattlerTagLapseType.TURN_END ], 1);
}
onAdd(pokemon: Pokemon): void {
super.onAdd(pokemon);
// "{Pokemon} is covered in powder!"
pokemon.scene.queueMessage(i18next.t("battlerTags:powderOnAdd", { pokemonNameWithAffix: getPokemonNameWithAffix(pokemon) }));
}
/**
* Applies Powder's effects before the tag owner uses a Fire-type move.
* Also causes the tag to expire at the end of turn.
* @param pokemon {@linkcode Pokemon} the owner of this tag
* @param lapseType {@linkcode BattlerTagLapseType} the type of lapse functionality to carry out
* @returns `true` if the tag should not expire after this lapse; `false` otherwise.
*/
lapse(pokemon: Pokemon, lapseType: BattlerTagLapseType): boolean {
if (lapseType === BattlerTagLapseType.PRE_MOVE) {
const movePhase = pokemon.scene.getCurrentPhase();
if (movePhase instanceof MovePhase) {
const move = movePhase.move.getMove();
const weather = pokemon.scene.arena.weather;
if (pokemon.getMoveType(move) === Type.FIRE && !(weather && weather.weatherType === WeatherType.HEAVY_RAIN && !weather.isEffectSuppressed(pokemon.scene))) {
movePhase.fail();
movePhase.showMoveText();
pokemon.scene.unshiftPhase(new CommonAnimPhase(pokemon.scene, pokemon.getBattlerIndex(), pokemon.getBattlerIndex(), CommonAnim.POWDER));
const cancelDamage = new BooleanHolder(false);
applyAbAttrs(BlockNonDirectDamageAbAttr, pokemon, cancelDamage);
if (!cancelDamage.value) {
pokemon.damageAndUpdate(Math.floor(pokemon.getMaxHp() / 4), HitResult.OTHER);
}
// "When the flame touched the powder\non the Pokémon, it exploded!"
pokemon.scene.queueMessage(i18next.t("battlerTags:powderLapse", { moveName: move.name }));
}
}
return true;
} else {
return super.lapse(pokemon, lapseType);
}
}
}
export class NightmareTag extends BattlerTag { export class NightmareTag extends BattlerTag {
constructor() { constructor() {
super(BattlerTagType.NIGHTMARE, BattlerTagLapseType.TURN_END, 1, Moves.NIGHTMARE); super(BattlerTagType.NIGHTMARE, BattlerTagLapseType.TURN_END, 1, Moves.NIGHTMARE);
@ -1085,10 +1138,6 @@ export class OctolockTag extends TrappedTag {
super(BattlerTagType.OCTOLOCK, BattlerTagLapseType.TURN_END, 1, Moves.OCTOLOCK, sourceId); super(BattlerTagType.OCTOLOCK, BattlerTagLapseType.TURN_END, 1, Moves.OCTOLOCK, sourceId);
} }
canAdd(pokemon: Pokemon): boolean {
return !pokemon.getTag(BattlerTagType.OCTOLOCK);
}
lapse(pokemon: Pokemon, lapseType: BattlerTagLapseType): boolean { lapse(pokemon: Pokemon, lapseType: BattlerTagLapseType): boolean {
const shouldLapse = lapseType !== BattlerTagLapseType.CUSTOM || super.lapse(pokemon, lapseType); const shouldLapse = lapseType !== BattlerTagLapseType.CUSTOM || super.lapse(pokemon, lapseType);
@ -2959,6 +3008,8 @@ export function getBattlerTag(tagType: BattlerTagType, turnCount: number, source
return new InfatuatedTag(sourceMove, sourceId); return new InfatuatedTag(sourceMove, sourceId);
case BattlerTagType.SEEDED: case BattlerTagType.SEEDED:
return new SeedTag(sourceId); return new SeedTag(sourceId);
case BattlerTagType.POWDER:
return new PowderTag();
case BattlerTagType.NIGHTMARE: case BattlerTagType.NIGHTMARE:
return new NightmareTag(); return new NightmareTag();
case BattlerTagType.FRENZY: case BattlerTagType.FRENZY:

View File

@ -1385,16 +1385,40 @@ export class UserHpDamageAttr extends FixedDamageAttr {
} }
export class TargetHalfHpDamageAttr extends FixedDamageAttr { export class TargetHalfHpDamageAttr extends FixedDamageAttr {
// the initial amount of hp the target had before the first hit
// used for multi lens
private initialHp: number;
constructor() { constructor() {
super(0); super(0);
} }
apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean {
(args[0] as Utils.IntegerHolder).value = Utils.toDmgValue(target.hp / 2); // first, determine if the hit is coming from multi lens or not
const lensCount = user.getHeldItems().find(i => i instanceof PokemonMultiHitModifier)?.getStackCount() ?? 0;
if (lensCount <= 0) {
// no multi lenses; we can just halve the target's hp and call it a day
(args[0] as Utils.NumberHolder).value = Utils.toDmgValue(target.hp / 2);
return true; return true;
} }
// figure out what hit # we're on
switch (user.turnData.hitCount - user.turnData.hitsLeft) {
case 0:
// first hit of move; update initialHp tracker
this.initialHp = target.hp;
default:
// multi lens added hit; use initialHp tracker to ensure correct damage
(args[0] as Utils.NumberHolder).value = Utils.toDmgValue(this.initialHp / 2);
return true;
break;
case lensCount + 1:
// parental bond added hit; calc damage as normal
(args[0] as Utils.NumberHolder).value = Utils.toDmgValue(target.hp / 2);
return true;
break;
}
}
getTargetBenefitScore(user: Pokemon, target: Pokemon, move: Move): number { getTargetBenefitScore(user: Pokemon, target: Pokemon, move: Move): number {
return target.getHpRatio() > 0.5 ? Math.floor(((target.getHpRatio() - 0.5) * -24) + 4) : -20; return target.getHpRatio() > 0.5 ? Math.floor(((target.getHpRatio() - 0.5) * -24) + 4) : -20;
} }
@ -1843,7 +1867,7 @@ export class FlameBurstAttr extends MoveEffectAttr {
applyAbAttrs(BlockNonDirectDamageAbAttr, targetAlly, cancelled); applyAbAttrs(BlockNonDirectDamageAbAttr, targetAlly, cancelled);
} }
if (cancelled.value || !targetAlly) { if (cancelled.value || !targetAlly || targetAlly.switchOutStatus) {
return false; return false;
} }
@ -1857,8 +1881,14 @@ export class FlameBurstAttr extends MoveEffectAttr {
} }
export class SacrificialFullRestoreAttr extends SacrificialAttr { export class SacrificialFullRestoreAttr extends SacrificialAttr {
constructor() { protected restorePP: boolean;
protected moveMessage: string;
constructor(restorePP: boolean, moveMessage: string) {
super(); super();
this.restorePP = restorePP;
this.moveMessage = moveMessage;
} }
apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean { apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean {
@ -1869,8 +1899,19 @@ export class SacrificialFullRestoreAttr extends SacrificialAttr {
// We don't know which party member will be chosen, so pick the highest max HP in the party // We don't know which party member will be chosen, so pick the highest max HP in the party
const maxPartyMemberHp = user.scene.getPlayerParty().map(p => p.getMaxHp()).reduce((maxHp: integer, hp: integer) => Math.max(hp, maxHp), 0); const maxPartyMemberHp = user.scene.getPlayerParty().map(p => p.getMaxHp()).reduce((maxHp: integer, hp: integer) => Math.max(hp, maxHp), 0);
user.scene.pushPhase(new PokemonHealPhase(user.scene, user.getBattlerIndex(), user.scene.pushPhase(
maxPartyMemberHp, i18next.t("moveTriggers:sacrificialFullRestore", { pokemonName: getPokemonNameWithAffix(user) }), true, false, false, true), true); new PokemonHealPhase(
user.scene,
user.getBattlerIndex(),
maxPartyMemberHp,
i18next.t(this.moveMessage, { pokemonName: getPokemonNameWithAffix(user) }),
true,
false,
false,
true,
false,
this.restorePP),
true);
return true; return true;
} }
@ -5967,50 +6008,113 @@ export class ForceSwitchOutAttr extends MoveEffectAttr {
* Check if Wimp Out/Emergency Exit activates due to being hit by U-turn or Volt Switch * Check if Wimp Out/Emergency Exit activates due to being hit by U-turn or Volt Switch
* If it did, the user of U-turn or Volt Switch will not be switched out. * If it did, the user of U-turn or Volt Switch will not be switched out.
*/ */
if (target.getAbility().hasAttr(PostDamageForceSwitchAbAttr) && if (target.getAbility().hasAttr(PostDamageForceSwitchAbAttr)
(move.id === Moves.U_TURN || move.id === Moves.VOLT_SWITCH || move.id === Moves.FLIP_TURN) && [ Moves.U_TURN, Moves.VOLT_SWITCH, Moves.FLIP_TURN ].includes(move.id)
) { ) {
if (this.hpDroppedBelowHalf(target)) { if (this.hpDroppedBelowHalf(target)) {
return false; return false;
} }
} }
// Switch out logic for the player's Pokemon
if (switchOutTarget.scene.getPlayerParty().filter((p) => p.isAllowedInBattle() && !p.isOnField()).length < 1) { // Find indices of off-field Pokemon that are eligible to be switched into
const eligibleNewIndices: number[] = [];
switchOutTarget.scene.getPlayerParty().forEach((pokemon, index) => {
if (pokemon.isAllowedInBattle() && !pokemon.isOnField()) {
eligibleNewIndices.push(index);
}
});
if (eligibleNewIndices.length < 1) {
return false; return false;
} }
if (switchOutTarget.hp > 0) { if (switchOutTarget.hp > 0) {
if (this.switchType === SwitchType.FORCE_SWITCH) {
switchOutTarget.leaveField(true);
const slotIndex = eligibleNewIndices[user.randSeedInt(eligibleNewIndices.length)];
user.scene.prependToPhase(
new SwitchSummonPhase(
user.scene,
this.switchType,
switchOutTarget.getFieldIndex(),
slotIndex,
false,
true
),
MoveEndPhase
);
} else {
switchOutTarget.leaveField(this.switchType === SwitchType.SWITCH); switchOutTarget.leaveField(this.switchType === SwitchType.SWITCH);
user.scene.prependToPhase(new SwitchPhase(user.scene, this.switchType, switchOutTarget.getFieldIndex(), true, true), MoveEndPhase); user.scene.prependToPhase(
new SwitchPhase(
user.scene,
this.switchType,
switchOutTarget.getFieldIndex(),
true,
true
),
MoveEndPhase
);
return true; return true;
} }
}
return false; return false;
} else if (user.scene.currentBattle.battleType !== BattleType.WILD) { } else if (user.scene.currentBattle.battleType !== BattleType.WILD) { // Switch out logic for enemy trainers
// Switch out logic for trainer battles // Find indices of off-field Pokemon that are eligible to be switched into
if (switchOutTarget.scene.getEnemyParty().filter((p) => p.isAllowedInBattle() && !p.isOnField()).length < 1) { const eligibleNewIndices: number[] = [];
switchOutTarget.scene.getEnemyParty().forEach((pokemon, index) => {
if (pokemon.isAllowedInBattle() && !pokemon.isOnField()) {
eligibleNewIndices.push(index);
}
});
if (eligibleNewIndices.length < 1) {
return false; return false;
} }
if (switchOutTarget.hp > 0) { if (switchOutTarget.hp > 0) {
// for opponent switching out if (this.switchType === SwitchType.FORCE_SWITCH) {
switchOutTarget.leaveField(this.switchType === SwitchType.SWITCH); switchOutTarget.leaveField(true);
user.scene.prependToPhase(new SwitchSummonPhase(user.scene, this.switchType, switchOutTarget.getFieldIndex(), const slotIndex = eligibleNewIndices[user.randSeedInt(eligibleNewIndices.length)];
(user.scene.currentBattle.trainer ? user.scene.currentBattle.trainer.getNextSummonIndex((switchOutTarget as EnemyPokemon).trainerSlot) : 0), user.scene.prependToPhase(
false, false), MoveEndPhase); new SwitchSummonPhase(
} user.scene,
this.switchType,
switchOutTarget.getFieldIndex(),
slotIndex,
false,
false
),
MoveEndPhase
);
} else { } else {
switchOutTarget.leaveField(this.switchType === SwitchType.SWITCH);
user.scene.prependToPhase(
new SwitchSummonPhase(
user.scene,
this.switchType,
switchOutTarget.getFieldIndex(),
(user.scene.currentBattle.trainer ? user.scene.currentBattle.trainer.getNextSummonIndex((switchOutTarget as EnemyPokemon).trainerSlot) : 0),
false,
false
),
MoveEndPhase
);
}
}
} else { // Switch out logic for wild pokemon
/** /**
* Check if Wimp Out/Emergency Exit activates due to being hit by U-turn or Volt Switch * Check if Wimp Out/Emergency Exit activates due to being hit by U-turn or Volt Switch
* If it did, the user of U-turn or Volt Switch will not be switched out. * If it did, the user of U-turn or Volt Switch will not be switched out.
*/ */
if (target.getAbility().hasAttr(PostDamageForceSwitchAbAttr) && if (target.getAbility().hasAttr(PostDamageForceSwitchAbAttr)
(move.id === Moves.U_TURN || move.id === Moves.VOLT_SWITCH) || move.id === Moves.FLIP_TURN) { && [ Moves.U_TURN, Moves.VOLT_SWITCH, Moves.FLIP_TURN ].includes(move.id)
) {
if (this.hpDroppedBelowHalf(target)) { if (this.hpDroppedBelowHalf(target)) {
return false; return false;
} }
} }
// Switch out logic for everything else (eg: WILD battles)
if (user.scene.currentBattle.waveIndex % 10 === 0) { if (user.scene.currentBattle.waveIndex % 10 === 0) {
return false; return false;
} }
@ -6035,7 +6139,7 @@ export class ForceSwitchOutAttr extends MoveEffectAttr {
user.scene.clearEnemyHeldItemModifiers(); user.scene.clearEnemyHeldItemModifiers();
if (switchOutTarget.hp) { if (switchOutTarget.hp) {
user.scene.pushPhase(new BattleEndPhase(user.scene)); user.scene.pushPhase(new BattleEndPhase(user.scene, false));
user.scene.pushPhase(new NewBattlePhase(user.scene)); user.scene.pushPhase(new NewBattlePhase(user.scene));
} }
} }
@ -6641,6 +6745,126 @@ export class CopyMoveAttr extends OverrideMoveEffectAttr {
} }
} }
/**
* Attribute used for moves that causes the target to repeat their last used move.
*
* Used for [Instruct](https://bulbapedia.bulbagarden.net/wiki/Instruct_(move)).
*/
export class RepeatMoveAttr extends MoveEffectAttr {
constructor() {
super(false, { trigger: MoveEffectTrigger.POST_APPLY }); // needed to ensure correct protect interaction
}
/**
* Forces the target to re-use their last used move again
*
* @param user {@linkcode Pokemon} that used the attack
* @param target {@linkcode Pokemon} targeted by the attack
* @param move N/A
* @param args N/A
* @returns `true` if the move succeeds
*/
apply(user: Pokemon, target: Pokemon, move: Move, args: any[]): boolean {
// get the last move used (excluding status based failures) as well as the corresponding moveset slot
const lastMove = target.getLastXMoves(-1).find(m => m.move !== Moves.NONE)!;
const movesetMove = target.getMoveset().find(m => m?.moveId === lastMove.move)!;
const moveTargets = lastMove.targets ?? [];
user.scene.queueMessage(i18next.t("moveTriggers:instructingMove", {
userPokemonName: getPokemonNameWithAffix(user),
targetPokemonName: getPokemonNameWithAffix(target)
}));
target.getMoveQueue().unshift({ move: lastMove.move, targets: moveTargets, ignorePP: false });
target.turnData.extraTurns++;
target.scene.appendToPhase(new MovePhase(target.scene, target, moveTargets, movesetMove), MoveEndPhase);
return true;
}
getCondition(): MoveConditionFunc {
return (user, target, move) => {
// TODO: Confirm behavior of instructing move known by target but called by another move
const lastMove = target.getLastXMoves(-1).find(m => m.move !== Moves.NONE);
const movesetMove = target.getMoveset().find(m => m?.moveId === lastMove?.move);
const moveTargets = lastMove?.targets ?? [];
// TODO: Add a way of adding moves to list procedurally rather than a pre-defined blacklist
const unrepeatablemoves = [
// Locking/Continually Executed moves
Moves.OUTRAGE,
Moves.RAGING_FURY,
Moves.ROLLOUT,
Moves.PETAL_DANCE,
Moves.THRASH,
Moves.ICE_BALL,
// Multi-turn Moves
Moves.BIDE,
Moves.SHELL_TRAP,
Moves.BEAK_BLAST,
Moves.FOCUS_PUNCH,
// "First Turn Only" moves
Moves.FAKE_OUT,
Moves.FIRST_IMPRESSION,
Moves.MAT_BLOCK,
// Moves with a recharge turn
Moves.HYPER_BEAM,
Moves.ETERNABEAM,
Moves.FRENZY_PLANT,
Moves.BLAST_BURN,
Moves.HYDRO_CANNON,
Moves.GIGA_IMPACT,
Moves.PRISMATIC_LASER,
Moves.ROAR_OF_TIME,
Moves.ROCK_WRECKER,
Moves.METEOR_ASSAULT,
// Charging & 2-turn moves
Moves.DIG,
Moves.FLY,
Moves.BOUNCE,
Moves.SHADOW_FORCE,
Moves.PHANTOM_FORCE,
Moves.DIVE,
Moves.ELECTRO_SHOT,
Moves.ICE_BURN,
Moves.GEOMANCY,
Moves.FREEZE_SHOCK,
Moves.SKY_DROP,
Moves.SKY_ATTACK,
Moves.SKULL_BASH,
Moves.SOLAR_BEAM,
Moves.SOLAR_BLADE,
Moves.METEOR_BEAM,
// Other moves
Moves.INSTRUCT,
Moves.KINGS_SHIELD,
Moves.SKETCH,
Moves.TRANSFORM,
Moves.MIMIC,
Moves.STRUGGLE,
// TODO: Add Max/G-Move blockage if or when they are implemented
];
if (!movesetMove // called move not in target's moveset (dancer, forgetting the move, etc.)
|| movesetMove.ppUsed === movesetMove.getMovePp() // move out of pp
|| allMoves[lastMove?.move ?? Moves.NONE].isChargingMove() // called move is a charging/recharging move
|| !moveTargets.length // called move has no targets
|| unrepeatablemoves.includes(lastMove?.move ?? Moves.NONE)) { // called move is explicitly in the banlist
return false;
}
return true;
};
}
getTargetBenefitScore(user: Pokemon, target: Pokemon, move: Move): integer {
// TODO: Make the AI acutally use instruct
/* Ideally, the AI would score instruct based on the scorings of the on-field pokemons'
* last used moves at the time of using Instruct (by the time the instructor gets to act)
* with respect to the user's side.
* In 99.9% of cases, this would be the pokemon's ally (unless the target had last
* used a move like Decorate on the user or its ally)
*/
return 2;
}
}
/** /**
* Attribute used for moves that reduce PP of the target's last used move. * Attribute used for moves that reduce PP of the target's last used move.
* Used for Spite. * Used for Spite.
@ -7455,6 +7679,8 @@ const failIfLastInPartyCondition: MoveConditionFunc = (user: Pokemon, target: Po
return party.some(pokemon => pokemon.isActive() && !pokemon.isOnField()); return party.some(pokemon => pokemon.isActive() && !pokemon.isOnField());
}; };
const failIfGhostTypeCondition: MoveConditionFunc = (user: Pokemon, target: Pokemon, move: Move) => !target.isOfType(Type.GHOST);
export type MoveAttrFilter = (attr: MoveAttr) => boolean; export type MoveAttrFilter = (attr: MoveAttr) => boolean;
function applyMoveAttrsInternal(attrFilter: MoveAttrFilter, user: Pokemon | null, target: Pokemon | null, move: Move, args: any[]): Promise<void> { function applyMoveAttrsInternal(attrFilter: MoveAttrFilter, user: Pokemon | null, target: Pokemon | null, move: Move, args: any[]): Promise<void> {
@ -7778,11 +8004,10 @@ export function initMoves() {
.windMove(), .windMove(),
new AttackMove(Moves.WING_ATTACK, Type.FLYING, MoveCategory.PHYSICAL, 60, 100, 35, -1, 0, 1), new AttackMove(Moves.WING_ATTACK, Type.FLYING, MoveCategory.PHYSICAL, 60, 100, 35, -1, 0, 1),
new StatusMove(Moves.WHIRLWIND, Type.NORMAL, -1, 20, -1, -6, 1) new StatusMove(Moves.WHIRLWIND, Type.NORMAL, -1, 20, -1, -6, 1)
.attr(ForceSwitchOutAttr) .attr(ForceSwitchOutAttr, false, SwitchType.FORCE_SWITCH)
.ignoresSubstitute() .ignoresSubstitute()
.hidesTarget() .hidesTarget()
.windMove() .windMove(),
.partial(), // Should force random switches
new ChargingAttackMove(Moves.FLY, Type.FLYING, MoveCategory.PHYSICAL, 90, 95, 15, -1, 0, 1) new ChargingAttackMove(Moves.FLY, Type.FLYING, MoveCategory.PHYSICAL, 90, 95, 15, -1, 0, 1)
.chargeText(i18next.t("moveTriggers:flewUpHigh", { pokemonName: "{USER}" })) .chargeText(i18next.t("moveTriggers:flewUpHigh", { pokemonName: "{USER}" }))
.chargeAttr(SemiInvulnerableAttr, BattlerTagType.FLYING) .chargeAttr(SemiInvulnerableAttr, BattlerTagType.FLYING)
@ -7858,10 +8083,9 @@ export function initMoves() {
.soundBased() .soundBased()
.target(MoveTarget.ALL_NEAR_ENEMIES), .target(MoveTarget.ALL_NEAR_ENEMIES),
new StatusMove(Moves.ROAR, Type.NORMAL, -1, 20, -1, -6, 1) new StatusMove(Moves.ROAR, Type.NORMAL, -1, 20, -1, -6, 1)
.attr(ForceSwitchOutAttr) .attr(ForceSwitchOutAttr, false, SwitchType.FORCE_SWITCH)
.soundBased() .soundBased()
.hidesTarget() .hidesTarget(),
.partial(), // Should force random switching
new StatusMove(Moves.SING, Type.NORMAL, 55, 15, -1, 0, 1) new StatusMove(Moves.SING, Type.NORMAL, 55, 15, -1, 0, 1)
.attr(StatusEffectAttr, StatusEffect.SLEEP) .attr(StatusEffectAttr, StatusEffect.SLEEP)
.soundBased(), .soundBased(),
@ -8205,6 +8429,7 @@ export function initMoves() {
new AttackMove(Moves.THIEF, Type.DARK, MoveCategory.PHYSICAL, 60, 100, 25, -1, 0, 2) new AttackMove(Moves.THIEF, Type.DARK, MoveCategory.PHYSICAL, 60, 100, 25, -1, 0, 2)
.attr(StealHeldItemChanceAttr, 0.3), .attr(StealHeldItemChanceAttr, 0.3),
new StatusMove(Moves.SPIDER_WEB, Type.BUG, -1, 10, -1, 0, 2) new StatusMove(Moves.SPIDER_WEB, Type.BUG, -1, 10, -1, 0, 2)
.condition(failIfGhostTypeCondition)
.attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1), .attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1),
new StatusMove(Moves.MIND_READER, Type.NORMAL, -1, 5, -1, 0, 2) new StatusMove(Moves.MIND_READER, Type.NORMAL, -1, 5, -1, 0, 2)
.attr(IgnoreAccuracyAttr), .attr(IgnoreAccuracyAttr),
@ -8341,6 +8566,7 @@ export function initMoves() {
new AttackMove(Moves.STEEL_WING, Type.STEEL, MoveCategory.PHYSICAL, 70, 90, 25, 10, 0, 2) new AttackMove(Moves.STEEL_WING, Type.STEEL, MoveCategory.PHYSICAL, 70, 90, 25, 10, 0, 2)
.attr(StatStageChangeAttr, [ Stat.DEF ], 1, true), .attr(StatStageChangeAttr, [ Stat.DEF ], 1, true),
new StatusMove(Moves.MEAN_LOOK, Type.NORMAL, -1, 5, -1, 0, 2) new StatusMove(Moves.MEAN_LOOK, Type.NORMAL, -1, 5, -1, 0, 2)
.condition(failIfGhostTypeCondition)
.attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1), .attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1),
new StatusMove(Moves.ATTRACT, Type.NORMAL, 100, 15, -1, 0, 2) new StatusMove(Moves.ATTRACT, Type.NORMAL, 100, 15, -1, 0, 2)
.attr(AddBattlerTagAttr, BattlerTagType.INFATUATED) .attr(AddBattlerTagAttr, BattlerTagType.INFATUATED)
@ -8460,7 +8686,7 @@ export function initMoves() {
.attr(StatStageChangeAttr, [ Stat.SPDEF ], -1) .attr(StatStageChangeAttr, [ Stat.SPDEF ], -1)
.ballBombMove(), .ballBombMove(),
new AttackMove(Moves.FUTURE_SIGHT, Type.PSYCHIC, MoveCategory.SPECIAL, 120, 100, 10, -1, 0, 2) new AttackMove(Moves.FUTURE_SIGHT, Type.PSYCHIC, MoveCategory.SPECIAL, 120, 100, 10, -1, 0, 2)
.partial() // cannot be used on multiple Pokemon on the same side in a double battle, hits immediately when called by Metronome/etc .partial() // cannot be used on multiple Pokemon on the same side in a double battle, hits immediately when called by Metronome/etc, should not apply abilities or held items if user is off the field
.ignoresProtect() .ignoresProtect()
.attr(DelayedAttackAttr, ArenaTagType.FUTURE_SIGHT, ChargeAnim.FUTURE_SIGHT_CHARGING, i18next.t("moveTriggers:foresawAnAttack", { pokemonName: "{USER}" })), .attr(DelayedAttackAttr, ArenaTagType.FUTURE_SIGHT, ChargeAnim.FUTURE_SIGHT_CHARGING, i18next.t("moveTriggers:foresawAnAttack", { pokemonName: "{USER}" })),
new AttackMove(Moves.ROCK_SMASH, Type.FIGHTING, MoveCategory.PHYSICAL, 40, 100, 15, 50, 0, 2) new AttackMove(Moves.ROCK_SMASH, Type.FIGHTING, MoveCategory.PHYSICAL, 40, 100, 15, 50, 0, 2)
@ -8720,6 +8946,7 @@ export function initMoves() {
new SelfStatusMove(Moves.IRON_DEFENSE, Type.STEEL, -1, 15, -1, 0, 3) new SelfStatusMove(Moves.IRON_DEFENSE, Type.STEEL, -1, 15, -1, 0, 3)
.attr(StatStageChangeAttr, [ Stat.DEF ], 2, true), .attr(StatStageChangeAttr, [ Stat.DEF ], 2, true),
new StatusMove(Moves.BLOCK, Type.NORMAL, -1, 5, -1, 0, 3) new StatusMove(Moves.BLOCK, Type.NORMAL, -1, 5, -1, 0, 3)
.condition(failIfGhostTypeCondition)
.attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1), .attr(AddBattlerTagAttr, BattlerTagType.TRAPPED, false, true, 1),
new StatusMove(Moves.HOWL, Type.NORMAL, -1, 40, -1, 0, 3) new StatusMove(Moves.HOWL, Type.NORMAL, -1, 40, -1, 0, 3)
.attr(StatStageChangeAttr, [ Stat.ATK ], 1) .attr(StatStageChangeAttr, [ Stat.ATK ], 1)
@ -8769,7 +8996,7 @@ export function initMoves() {
.attr(ConfuseAttr) .attr(ConfuseAttr)
.pulseMove(), .pulseMove(),
new AttackMove(Moves.DOOM_DESIRE, Type.STEEL, MoveCategory.SPECIAL, 140, 100, 5, -1, 0, 3) new AttackMove(Moves.DOOM_DESIRE, Type.STEEL, MoveCategory.SPECIAL, 140, 100, 5, -1, 0, 3)
.partial() // cannot be used on multiple Pokemon on the same side in a double battle, hits immediately when called by Metronome/etc .partial() // cannot be used on multiple Pokemon on the same side in a double battle, hits immediately when called by Metronome/etc, should not apply abilities or held items if user is off the field
.ignoresProtect() .ignoresProtect()
.attr(DelayedAttackAttr, ArenaTagType.DOOM_DESIRE, ChargeAnim.DOOM_DESIRE_CHARGING, i18next.t("moveTriggers:choseDoomDesireAsDestiny", { pokemonName: "{USER}" })), .attr(DelayedAttackAttr, ArenaTagType.DOOM_DESIRE, ChargeAnim.DOOM_DESIRE_CHARGING, i18next.t("moveTriggers:choseDoomDesireAsDestiny", { pokemonName: "{USER}" })),
new AttackMove(Moves.PSYCHO_BOOST, Type.PSYCHIC, MoveCategory.SPECIAL, 140, 90, 5, -1, 0, 3) new AttackMove(Moves.PSYCHO_BOOST, Type.PSYCHIC, MoveCategory.SPECIAL, 140, 90, 5, -1, 0, 3)
@ -8795,7 +9022,7 @@ export function initMoves() {
.attr(GyroBallPowerAttr) .attr(GyroBallPowerAttr)
.ballBombMove(), .ballBombMove(),
new SelfStatusMove(Moves.HEALING_WISH, Type.PSYCHIC, -1, 10, -1, 0, 4) new SelfStatusMove(Moves.HEALING_WISH, Type.PSYCHIC, -1, 10, -1, 0, 4)
.attr(SacrificialFullRestoreAttr) .attr(SacrificialFullRestoreAttr, false, "moveTriggers:sacrificialFullRestore")
.triageMove(), .triageMove(),
new AttackMove(Moves.BRINE, Type.WATER, MoveCategory.SPECIAL, 65, 100, 10, -1, 0, 4) new AttackMove(Moves.BRINE, Type.WATER, MoveCategory.SPECIAL, 65, 100, 10, -1, 0, 4)
.attr(MovePowerMultiplierAttr, (user, target, move) => target.getHpRatio() < 0.5 ? 2 : 1), .attr(MovePowerMultiplierAttr, (user, target, move) => target.getHpRatio() < 0.5 ? 2 : 1),
@ -9072,10 +9299,9 @@ export function initMoves() {
new AttackMove(Moves.SPACIAL_REND, Type.DRAGON, MoveCategory.SPECIAL, 100, 95, 5, -1, 0, 4) new AttackMove(Moves.SPACIAL_REND, Type.DRAGON, MoveCategory.SPECIAL, 100, 95, 5, -1, 0, 4)
.attr(HighCritAttr), .attr(HighCritAttr),
new SelfStatusMove(Moves.LUNAR_DANCE, Type.PSYCHIC, -1, 10, -1, 0, 4) new SelfStatusMove(Moves.LUNAR_DANCE, Type.PSYCHIC, -1, 10, -1, 0, 4)
.attr(SacrificialAttrOnHit) .attr(SacrificialFullRestoreAttr, true, "moveTriggers:lunarDanceRestore")
.danceMove() .danceMove()
.triageMove() .triageMove(),
.unimplemented(),
new AttackMove(Moves.CRUSH_GRIP, Type.NORMAL, MoveCategory.PHYSICAL, -1, 100, 5, -1, 0, 4) new AttackMove(Moves.CRUSH_GRIP, Type.NORMAL, MoveCategory.PHYSICAL, -1, 100, 5, -1, 0, 4)
.attr(OpponentHighHpPowerAttr, 120), .attr(OpponentHighHpPowerAttr, 120),
new AttackMove(Moves.MAGMA_STORM, Type.FIRE, MoveCategory.SPECIAL, 100, 75, 5, -1, 0, 4) new AttackMove(Moves.MAGMA_STORM, Type.FIRE, MoveCategory.SPECIAL, 100, 75, 5, -1, 0, 4)
@ -9225,8 +9451,8 @@ export function initMoves() {
.attr(StatStageChangeAttr, [ Stat.ATK ], 1, true) .attr(StatStageChangeAttr, [ Stat.ATK ], 1, true)
.attr(StatStageChangeAttr, [ Stat.SPD ], 2, true), .attr(StatStageChangeAttr, [ Stat.SPD ], 2, true),
new AttackMove(Moves.CIRCLE_THROW, Type.FIGHTING, MoveCategory.PHYSICAL, 60, 90, 10, -1, -6, 5) new AttackMove(Moves.CIRCLE_THROW, Type.FIGHTING, MoveCategory.PHYSICAL, 60, 90, 10, -1, -6, 5)
.attr(ForceSwitchOutAttr) .attr(ForceSwitchOutAttr, false, SwitchType.FORCE_SWITCH)
.partial(), // Should force random switches .hidesTarget(),
new AttackMove(Moves.INCINERATE, Type.FIRE, MoveCategory.SPECIAL, 60, 100, 15, -1, 0, 5) new AttackMove(Moves.INCINERATE, Type.FIRE, MoveCategory.SPECIAL, 60, 100, 15, -1, 0, 5)
.target(MoveTarget.ALL_NEAR_ENEMIES) .target(MoveTarget.ALL_NEAR_ENEMIES)
.attr(RemoveHeldItemAttr, true), .attr(RemoveHeldItemAttr, true),
@ -9294,9 +9520,8 @@ export function initMoves() {
new AttackMove(Moves.FROST_BREATH, Type.ICE, MoveCategory.SPECIAL, 60, 90, 10, 100, 0, 5) new AttackMove(Moves.FROST_BREATH, Type.ICE, MoveCategory.SPECIAL, 60, 90, 10, 100, 0, 5)
.attr(CritOnlyAttr), .attr(CritOnlyAttr),
new AttackMove(Moves.DRAGON_TAIL, Type.DRAGON, MoveCategory.PHYSICAL, 60, 90, 10, -1, -6, 5) new AttackMove(Moves.DRAGON_TAIL, Type.DRAGON, MoveCategory.PHYSICAL, 60, 90, 10, -1, -6, 5)
.attr(ForceSwitchOutAttr) .attr(ForceSwitchOutAttr, false, SwitchType.FORCE_SWITCH)
.hidesTarget() .hidesTarget(),
.partial(), // Should force random switches
new SelfStatusMove(Moves.WORK_UP, Type.NORMAL, -1, 30, -1, 0, 5) new SelfStatusMove(Moves.WORK_UP, Type.NORMAL, -1, 30, -1, 0, 5)
.attr(StatStageChangeAttr, [ Stat.ATK, Stat.SPATK ], 1, true), .attr(StatStageChangeAttr, [ Stat.ATK, Stat.SPATK ], 1, true),
new AttackMove(Moves.ELECTROWEB, Type.ELECTRIC, MoveCategory.SPECIAL, 55, 95, 15, 100, 0, 5) new AttackMove(Moves.ELECTROWEB, Type.ELECTRIC, MoveCategory.SPECIAL, 55, 95, 15, 100, 0, 5)
@ -9526,9 +9751,9 @@ export function initMoves() {
.attr(StatStageChangeAttr, [ Stat.ATK, Stat.SPATK, Stat.SPD ], -1, false, { condition: (user, target, move) => target.status?.effect === StatusEffect.POISON || target.status?.effect === StatusEffect.TOXIC }) .attr(StatStageChangeAttr, [ Stat.ATK, Stat.SPATK, Stat.SPD ], -1, false, { condition: (user, target, move) => target.status?.effect === StatusEffect.POISON || target.status?.effect === StatusEffect.TOXIC })
.target(MoveTarget.ALL_NEAR_ENEMIES), .target(MoveTarget.ALL_NEAR_ENEMIES),
new StatusMove(Moves.POWDER, Type.BUG, 100, 20, -1, 1, 6) new StatusMove(Moves.POWDER, Type.BUG, 100, 20, -1, 1, 6)
.attr(AddBattlerTagAttr, BattlerTagType.POWDER, false, true)
.ignoresSubstitute() .ignoresSubstitute()
.powderMove() .powderMove(),
.unimplemented(),
new ChargingSelfStatusMove(Moves.GEOMANCY, Type.FAIRY, -1, 10, -1, 0, 6) new ChargingSelfStatusMove(Moves.GEOMANCY, Type.FAIRY, -1, 10, -1, 0, 6)
.chargeText(i18next.t("moveTriggers:isChargingPower", { pokemonName: "{USER}" })) .chargeText(i18next.t("moveTriggers:isChargingPower", { pokemonName: "{USER}" }))
.attr(StatStageChangeAttr, [ Stat.SPATK, Stat.SPDEF, Stat.SPD ], 2, true) .attr(StatStageChangeAttr, [ Stat.SPATK, Stat.SPDEF, Stat.SPD ], 2, true)
@ -9806,7 +10031,8 @@ export function initMoves() {
.attr(StatStageChangeAttr, [ Stat.ATK ], -1), .attr(StatStageChangeAttr, [ Stat.ATK ], -1),
new StatusMove(Moves.INSTRUCT, Type.PSYCHIC, -1, 15, -1, 0, 7) new StatusMove(Moves.INSTRUCT, Type.PSYCHIC, -1, 15, -1, 0, 7)
.ignoresSubstitute() .ignoresSubstitute()
.unimplemented(), .attr(RepeatMoveAttr)
.edgeCase(), // incorrect interactions with Gigaton Hammer, Blood Moon & Torment
new AttackMove(Moves.BEAK_BLAST, Type.FLYING, MoveCategory.PHYSICAL, 100, 100, 15, -1, -3, 7) new AttackMove(Moves.BEAK_BLAST, Type.FLYING, MoveCategory.PHYSICAL, 100, 100, 15, -1, -3, 7)
.attr(BeakBlastHeaderAttr) .attr(BeakBlastHeaderAttr)
.ballBombMove() .ballBombMove()
@ -10015,6 +10241,7 @@ export function initMoves() {
.attr(EatBerryAttr) .attr(EatBerryAttr)
.target(MoveTarget.ALL), .target(MoveTarget.ALL),
new StatusMove(Moves.OCTOLOCK, Type.FIGHTING, 100, 15, -1, 0, 8) new StatusMove(Moves.OCTOLOCK, Type.FIGHTING, 100, 15, -1, 0, 8)
.condition(failIfGhostTypeCondition)
.attr(AddBattlerTagAttr, BattlerTagType.OCTOLOCK, false, true, 1), .attr(AddBattlerTagAttr, BattlerTagType.OCTOLOCK, false, true, 1),
new AttackMove(Moves.BOLT_BEAK, Type.ELECTRIC, MoveCategory.PHYSICAL, 85, 100, 10, -1, 0, 8) new AttackMove(Moves.BOLT_BEAK, Type.ELECTRIC, MoveCategory.PHYSICAL, 85, 100, 10, -1, 0, 8)
.attr(FirstAttackDoublePowerAttr), .attr(FirstAttackDoublePowerAttr),
@ -10557,6 +10784,7 @@ export function initMoves() {
new AttackMove(Moves.TWIN_BEAM, Type.PSYCHIC, MoveCategory.SPECIAL, 40, 100, 10, -1, 0, 9) new AttackMove(Moves.TWIN_BEAM, Type.PSYCHIC, MoveCategory.SPECIAL, 40, 100, 10, -1, 0, 9)
.attr(MultiHitAttr, MultiHitType._2), .attr(MultiHitAttr, MultiHitType._2),
new AttackMove(Moves.RAGE_FIST, Type.GHOST, MoveCategory.PHYSICAL, 50, 100, 10, -1, 0, 9) new AttackMove(Moves.RAGE_FIST, Type.GHOST, MoveCategory.PHYSICAL, 50, 100, 10, -1, 0, 9)
.partial() // Counter resets every wave instead of on arena reset
.attr(HitCountPowerAttr) .attr(HitCountPowerAttr)
.punchingMove(), .punchingMove(),
new AttackMove(Moves.ARMOR_CANNON, Type.FIRE, MoveCategory.SPECIAL, 120, 100, 5, -1, 0, 9) new AttackMove(Moves.ARMOR_CANNON, Type.FIRE, MoveCategory.SPECIAL, 120, 100, 5, -1, 0, 9)

View File

@ -216,6 +216,7 @@ export const AbsoluteAvariceEncounter: MysteryEncounter =
species: getPokemonSpecies(Species.GREEDENT), species: getPokemonSpecies(Species.GREEDENT),
isBoss: true, isBoss: true,
bossSegments: 3, bossSegments: 3,
shiny: false, // Shiny lock because of consistency issues between the different options
moveSet: [ Moves.THRASH, Moves.BODY_PRESS, Moves.STUFF_CHEEKS, Moves.CRUNCH ], moveSet: [ Moves.THRASH, Moves.BODY_PRESS, Moves.STUFF_CHEEKS, Moves.CRUNCH ],
modifierConfigs: bossModifierConfigs, modifierConfigs: bossModifierConfigs,
tags: [ BattlerTagType.MYSTERY_ENCOUNTER_POST_SUMMON ], tags: [ BattlerTagType.MYSTERY_ENCOUNTER_POST_SUMMON ],
@ -353,9 +354,9 @@ export const AbsoluteAvariceEncounter: MysteryEncounter =
}) })
.withOptionPhase(async (scene: BattleScene) => { .withOptionPhase(async (scene: BattleScene) => {
// Let it have the food // Let it have the food
// Greedent joins the team, level equal to 2 below highest party member // Greedent joins the team, level equal to 2 below highest party member (shiny locked)
const level = getHighestLevelPlayerPokemon(scene, false, true).level - 2; const level = getHighestLevelPlayerPokemon(scene, false, true).level - 2;
const greedent = new EnemyPokemon(scene, getPokemonSpecies(Species.GREEDENT), level, TrainerSlot.NONE, false); const greedent = new EnemyPokemon(scene, getPokemonSpecies(Species.GREEDENT), level, TrainerSlot.NONE, false, true);
greedent.moveset = [ new PokemonMove(Moves.THRASH), new PokemonMove(Moves.BODY_PRESS), new PokemonMove(Moves.STUFF_CHEEKS), new PokemonMove(Moves.SLACK_OFF) ]; greedent.moveset = [ new PokemonMove(Moves.THRASH), new PokemonMove(Moves.BODY_PRESS), new PokemonMove(Moves.STUFF_CHEEKS), new PokemonMove(Moves.SLACK_OFF) ];
greedent.passive = true; greedent.passive = true;

View File

@ -13,7 +13,7 @@ import {
ModifierTypeOption, modifierTypes, ModifierTypeOption, modifierTypes,
regenerateModifierPoolThresholds, regenerateModifierPoolThresholds,
} from "#app/modifier/modifier-type"; } from "#app/modifier/modifier-type";
import { randSeedInt } from "#app/utils"; import { randSeedInt, randSeedItem } from "#app/utils";
import { BattlerTagType } from "#enums/battler-tag-type"; import { BattlerTagType } from "#enums/battler-tag-type";
import { MysteryEncounterType } from "#enums/mystery-encounter-type"; import { MysteryEncounterType } from "#enums/mystery-encounter-type";
import BattleScene from "#app/battle-scene"; import BattleScene from "#app/battle-scene";
@ -31,6 +31,7 @@ import { BerryType } from "#enums/berry-type";
import { PERMANENT_STATS, Stat } from "#enums/stat"; import { PERMANENT_STATS, Stat } from "#enums/stat";
import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase"; import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import PokemonSpecies, { getPokemonSpecies } from "#app/data/pokemon-species";
/** the i18n namespace for the encounter */ /** the i18n namespace for the encounter */
const namespace = "mysteryEncounters/berriesAbound"; const namespace = "mysteryEncounters/berriesAbound";
@ -58,7 +59,14 @@ export const BerriesAboundEncounter: MysteryEncounter =
// Calculate boss mon // Calculate boss mon
const level = getEncounterPokemonLevelForWave(scene, STANDARD_ENCOUNTER_BOOSTED_LEVEL_MODIFIER); const level = getEncounterPokemonLevelForWave(scene, STANDARD_ENCOUNTER_BOOSTED_LEVEL_MODIFIER);
const bossSpecies = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true); let bossSpecies: PokemonSpecies;
if (scene.eventManager.isEventActive() && scene.eventManager.activeEvent()?.uncommonBreedEncounters && randSeedInt(2) === 1) {
const eventEncounter = randSeedItem(scene.eventManager.activeEvent()!.uncommonBreedEncounters!);
const levelSpecies = getPokemonSpecies(eventEncounter.species).getWildSpeciesForLevel(level, eventEncounter.allowEvolution ?? false, true, scene.gameMode);
bossSpecies = getPokemonSpecies( levelSpecies );
} else {
bossSpecies = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true);
}
const bossPokemon = new EnemyPokemon(scene, bossSpecies, level, TrainerSlot.NONE, true); const bossPokemon = new EnemyPokemon(scene, bossSpecies, level, TrainerSlot.NONE, true);
encounter.setDialogueToken("enemyPokemon", getPokemonNameWithAffix(bossPokemon)); encounter.setDialogueToken("enemyPokemon", getPokemonNameWithAffix(bossPokemon));
const config: EnemyPartyConfig = { const config: EnemyPartyConfig = {
@ -98,7 +106,9 @@ export const BerriesAboundEncounter: MysteryEncounter =
tint: 0.25, tint: 0.25,
x: -5, x: -5,
repeat: true, repeat: true,
isPokemon: true isPokemon: true,
isShiny: bossPokemon.shiny,
variant: bossPokemon.variant
} }
]; ];

View File

@ -276,6 +276,8 @@ export const ClowningAroundEncounter: MysteryEncounter =
generateItemsOfTier(scene, mostHeldItemsPokemon, numBerries, "Berries"); generateItemsOfTier(scene, mostHeldItemsPokemon, numBerries, "Berries");
// Shuffle Transferable held items in the same tier (only shuffles Ultra and Rogue atm) // Shuffle Transferable held items in the same tier (only shuffles Ultra and Rogue atm)
// For the purpose of this ME, Soothe Bells and Lucky Eggs are counted as Ultra tier
// And Golden Eggs as Rogue tier
let numUltra = 0; let numUltra = 0;
let numRogue = 0; let numRogue = 0;
items.filter(m => m.isTransferable && !(m instanceof BerryModifier)) items.filter(m => m.isTransferable && !(m instanceof BerryModifier))
@ -285,7 +287,7 @@ export const ClowningAroundEncounter: MysteryEncounter =
if (type.id === "GOLDEN_EGG" || tier === ModifierTier.ROGUE) { if (type.id === "GOLDEN_EGG" || tier === ModifierTier.ROGUE) {
numRogue += m.stackCount; numRogue += m.stackCount;
scene.removeModifier(m); scene.removeModifier(m);
} else if (type.id === "LUCKY_EGG" || tier === ModifierTier.ULTRA) { } else if (type.id === "LUCKY_EGG" || type.id === "SOOTHE_BELL" || tier === ModifierTier.ULTRA) {
numUltra += m.stackCount; numUltra += m.stackCount;
scene.removeModifier(m); scene.removeModifier(m);
} }
@ -456,7 +458,6 @@ function generateItemsOfTier(scene: BattleScene, pokemon: PlayerPokemon, numItem
[ modifierTypes.LEFTOVERS, 4 ], [ modifierTypes.LEFTOVERS, 4 ],
[ modifierTypes.SHELL_BELL, 4 ], [ modifierTypes.SHELL_BELL, 4 ],
[ modifierTypes.SOUL_DEW, 10 ], [ modifierTypes.SOUL_DEW, 10 ],
[ modifierTypes.SOOTHE_BELL, 3 ],
[ modifierTypes.SCOPE_LENS, 1 ], [ modifierTypes.SCOPE_LENS, 1 ],
[ modifierTypes.BATON, 1 ], [ modifierTypes.BATON, 1 ],
[ modifierTypes.FOCUS_BAND, 5 ], [ modifierTypes.FOCUS_BAND, 5 ],

View File

@ -92,9 +92,13 @@ export const DancingLessonsEncounter: MysteryEncounter =
.withCatchAllowed(true) .withCatchAllowed(true)
.withFleeAllowed(false) .withFleeAllowed(false)
.withOnVisualsStart((scene: BattleScene) => { .withOnVisualsStart((scene: BattleScene) => {
const danceAnim = new EncounterBattleAnim(EncounterAnim.DANCE, scene.getEnemyPokemon()!, scene.getPlayerPokemon()!); const oricorio = scene.getEnemyPokemon()!;
danceAnim.play(scene); const danceAnim = new EncounterBattleAnim(EncounterAnim.DANCE, oricorio, scene.getPlayerPokemon()!);
danceAnim.play(scene, false, () => {
if (oricorio.shiny) {
oricorio.sparkle();
}
});
return true; return true;
}) })
.withIntroDialogue([ .withIntroDialogue([
@ -136,7 +140,7 @@ export const DancingLessonsEncounter: MysteryEncounter =
} }
const oricorioData = new PokemonData(enemyPokemon); const oricorioData = new PokemonData(enemyPokemon);
const oricorio = scene.addEnemyPokemon(species, level, TrainerSlot.NONE, false, oricorioData); const oricorio = scene.addEnemyPokemon(species, level, TrainerSlot.NONE, false, false, oricorioData);
// Adds a real Pokemon sprite to the field (required for the animation) // Adds a real Pokemon sprite to the field (required for the animation)
scene.getEnemyParty().forEach(enemyPokemon => { scene.getEnemyParty().forEach(enemyPokemon => {

View File

@ -8,7 +8,7 @@ import { getPokemonSpecies } from "#app/data/pokemon-species";
import MysteryEncounter, { MysteryEncounterBuilder } from "#app/data/mystery-encounters/mystery-encounter"; import MysteryEncounter, { MysteryEncounterBuilder } from "#app/data/mystery-encounters/mystery-encounter";
import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option"; import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option";
import { EnemyPartyConfig, EnemyPokemonConfig, initBattleWithEnemyConfig, leaveEncounterWithoutBattle, } from "../utils/encounter-phase-utils"; import { EnemyPartyConfig, EnemyPokemonConfig, initBattleWithEnemyConfig, leaveEncounterWithoutBattle, } from "../utils/encounter-phase-utils";
import { getRandomPlayerPokemon, getRandomSpeciesByStarterTier } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { getRandomPlayerPokemon, getRandomSpeciesByStarterCost } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import { MysteryEncounterTier } from "#enums/mystery-encounter-tier"; import { MysteryEncounterTier } from "#enums/mystery-encounter-tier";
import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode"; import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode";
import { ModifierRewardPhase } from "#app/phases/modifier-reward-phase"; import { ModifierRewardPhase } from "#app/phases/modifier-reward-phase";
@ -174,7 +174,7 @@ export const DarkDealEncounter: MysteryEncounter =
const roll = randSeedInt(100); const roll = randSeedInt(100);
const starterTier: number | [number, number] = const starterTier: number | [number, number] =
roll >= 65 ? 6 : roll >= 15 ? 7 : roll >= 5 ? 8 : [ 9, 10 ]; roll >= 65 ? 6 : roll >= 15 ? 7 : roll >= 5 ? 8 : [ 9, 10 ];
const bossSpecies = getPokemonSpecies(getRandomSpeciesByStarterTier(starterTier, excludedBosses, bossTypes)); const bossSpecies = getPokemonSpecies(getRandomSpeciesByStarterCost(starterTier, excludedBosses, bossTypes));
const pokemonConfig: EnemyPokemonConfig = { const pokemonConfig: EnemyPokemonConfig = {
species: bossSpecies, species: bossSpecies,
isBoss: true, isBoss: true,

View File

@ -13,6 +13,7 @@ import { modifierTypes, PokemonHeldItemModifierType } from "#app/modifier/modifi
import { ModifierRewardPhase } from "#app/phases/modifier-reward-phase"; import { ModifierRewardPhase } from "#app/phases/modifier-reward-phase";
import i18next from "#app/plugins/i18n"; import i18next from "#app/plugins/i18n";
import { OptionSelectItem } from "#app/ui/abstact-option-select-ui-handler"; import { OptionSelectItem } from "#app/ui/abstact-option-select-ui-handler";
import { randSeedItem } from "#app/utils";
import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode"; import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode";
import { MysteryEncounterTier } from "#enums/mystery-encounter-tier"; import { MysteryEncounterTier } from "#enums/mystery-encounter-tier";
import { MysteryEncounterType } from "#enums/mystery-encounter-type"; import { MysteryEncounterType } from "#enums/mystery-encounter-type";
@ -33,7 +34,24 @@ const OPTION_3_DISALLOWED_MODIFIERS = [
"PokemonBaseStatTotalModifier" "PokemonBaseStatTotalModifier"
]; ];
const DELIBIRDY_MONEY_PRICE_MULTIPLIER = 2; const DELIBIRDY_MONEY_PRICE_MULTIPLIER = 1.5;
const doEventReward = (scene: BattleScene) => {
const event_buff = scene.eventManager.activeEvent()?.delibirdyBuff ?? [];
if (event_buff.length > 0) {
const candidates = event_buff.filter((c => {
const mtype = generateModifierType(scene, modifierTypes[c]);
const existingCharm = scene.findModifier(m => m.type.id === mtype?.id);
return !(existingCharm && existingCharm.getStackCount() >= existingCharm.getMaxStackCount(scene));
}));
if (candidates.length > 0) {
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes[randSeedItem(candidates)]));
} else {
// At max stacks, give a Voucher instead
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.VOUCHER));
}
}
};
/** /**
* Delibird-y encounter. * Delibird-y encounter.
@ -42,7 +60,8 @@ const DELIBIRDY_MONEY_PRICE_MULTIPLIER = 2;
*/ */
export const DelibirdyEncounter: MysteryEncounter = export const DelibirdyEncounter: MysteryEncounter =
MysteryEncounterBuilder.withEncounterType(MysteryEncounterType.DELIBIRDY) MysteryEncounterBuilder.withEncounterType(MysteryEncounterType.DELIBIRDY)
.withEncounterTier(MysteryEncounterTier.GREAT) .withMaxAllowedEncounters(4)
.withEncounterTier(MysteryEncounterTier.COMMON) //Change back after event!
.withSceneWaveRangeRequirement(...CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES) .withSceneWaveRangeRequirement(...CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES)
.withSceneRequirement(new MoneyRequirement(0, DELIBIRDY_MONEY_PRICE_MULTIPLIER)) // Must have enough money for it to spawn at the very least .withSceneRequirement(new MoneyRequirement(0, DELIBIRDY_MONEY_PRICE_MULTIPLIER)) // Must have enough money for it to spawn at the very least
.withPrimaryPokemonRequirement( .withPrimaryPokemonRequirement(
@ -136,8 +155,10 @@ export const DelibirdyEncounter: MysteryEncounter =
await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell); await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell);
scene.playSound("item_fanfare"); scene.playSound("item_fanfare");
await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true); await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true);
doEventReward(scene);
} else { } else {
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.AMULET_COIN)); scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.AMULET_COIN));
doEventReward(scene);
} }
leaveEncounterWithoutBattle(scene, true); leaveEncounterWithoutBattle(scene, true);
@ -211,8 +232,10 @@ export const DelibirdyEncounter: MysteryEncounter =
await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell); await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell);
scene.playSound("item_fanfare"); scene.playSound("item_fanfare");
await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true); await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true);
doEventReward(scene);
} else { } else {
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.CANDY_JAR)); scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.CANDY_JAR));
doEventReward(scene);
} }
} else { } else {
// Check if the player has max stacks of that Berry Pouch already // Check if the player has max stacks of that Berry Pouch already
@ -224,8 +247,10 @@ export const DelibirdyEncounter: MysteryEncounter =
await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell); await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerPokemon()!, shellBell);
scene.playSound("item_fanfare"); scene.playSound("item_fanfare");
await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true); await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true);
doEventReward(scene);
} else { } else {
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.BERRY_POUCH)); scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.BERRY_POUCH));
doEventReward(scene);
} }
} }
@ -300,8 +325,10 @@ export const DelibirdyEncounter: MysteryEncounter =
await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerParty()[0], shellBell); await applyModifierTypeToPlayerPokemon(scene, scene.getPlayerParty()[0], shellBell);
scene.playSound("item_fanfare"); scene.playSound("item_fanfare");
await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true); await showEncounterText(scene, i18next.t("battle:rewardGain", { modifierName: shellBell.name }), null, undefined, true);
doEventReward(scene);
} else { } else {
scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.HEALING_CHARM)); scene.unshiftPhase(new ModifierRewardPhase(scene, modifierTypes.HEALING_CHARM));
doEventReward(scene);
} }
chosenPokemon.loseHeldItem(modifier, false); chosenPokemon.loseHeldItem(modifier, false);

View File

@ -26,9 +26,10 @@ import { getEncounterPokemonLevelForWave, getSpriteKeysFromPokemon, STANDARD_ENC
import PokemonData from "#app/system/pokemon-data"; import PokemonData from "#app/system/pokemon-data";
import { BattlerTagType } from "#enums/battler-tag-type"; import { BattlerTagType } from "#enums/battler-tag-type";
import { queueEncounterMessage } from "#app/data/mystery-encounters/utils/encounter-dialogue-utils"; import { queueEncounterMessage } from "#app/data/mystery-encounters/utils/encounter-dialogue-utils";
import { randSeedInt } from "#app/utils"; import { randSeedInt, randSeedItem } from "#app/utils";
import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase"; import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import PokemonSpecies, { getPokemonSpecies } from "#app/data/pokemon-species";
/** the i18n namespace for the encounter */ /** the i18n namespace for the encounter */
const namespace = "mysteryEncounters/fightOrFlight"; const namespace = "mysteryEncounters/fightOrFlight";
@ -56,7 +57,14 @@ export const FightOrFlightEncounter: MysteryEncounter =
// Calculate boss mon // Calculate boss mon
const level = getEncounterPokemonLevelForWave(scene, STANDARD_ENCOUNTER_BOOSTED_LEVEL_MODIFIER); const level = getEncounterPokemonLevelForWave(scene, STANDARD_ENCOUNTER_BOOSTED_LEVEL_MODIFIER);
const bossSpecies = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true); let bossSpecies: PokemonSpecies;
if (scene.eventManager.isEventActive() && scene.eventManager.activeEvent()?.uncommonBreedEncounters && randSeedInt(2) === 1) {
const eventEncounter = randSeedItem(scene.eventManager.activeEvent()!.uncommonBreedEncounters!);
const levelSpecies = getPokemonSpecies(eventEncounter.species).getWildSpeciesForLevel(level, eventEncounter.allowEvolution ?? false, true, scene.gameMode);
bossSpecies = getPokemonSpecies( levelSpecies );
} else {
bossSpecies = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true);
}
const bossPokemon = new EnemyPokemon(scene, bossSpecies, level, TrainerSlot.NONE, true); const bossPokemon = new EnemyPokemon(scene, bossSpecies, level, TrainerSlot.NONE, true);
encounter.setDialogueToken("enemyPokemon", bossPokemon.getNameToRender()); encounter.setDialogueToken("enemyPokemon", bossPokemon.getNameToRender());
const config: EnemyPartyConfig = { const config: EnemyPartyConfig = {
@ -114,7 +122,9 @@ export const FightOrFlightEncounter: MysteryEncounter =
tint: 0.25, tint: 0.25,
x: -5, x: -5,
repeat: true, repeat: true,
isPokemon: true isPokemon: true,
isShiny: bossPokemon.shiny,
variant: bossPokemon.variant
}, },
]; ];

View File

@ -194,10 +194,10 @@ async function summonPlayerPokemon(scene: BattleScene) {
playerAnimationPromise = summonPlayerPokemonAnimation(scene, playerPokemon); playerAnimationPromise = summonPlayerPokemonAnimation(scene, playerPokemon);
}); });
// Also loads Wobbuffet data // Also loads Wobbuffet data (cannot be shiny)
const enemySpecies = getPokemonSpecies(Species.WOBBUFFET); const enemySpecies = getPokemonSpecies(Species.WOBBUFFET);
scene.currentBattle.enemyParty = []; scene.currentBattle.enemyParty = [];
const wobbuffet = scene.addEnemyPokemon(enemySpecies, encounter.misc.playerPokemon.level, TrainerSlot.NONE, false); const wobbuffet = scene.addEnemyPokemon(enemySpecies, encounter.misc.playerPokemon.level, TrainerSlot.NONE, false, true);
wobbuffet.ivs = [ 0, 0, 0, 0, 0, 0 ]; wobbuffet.ivs = [ 0, 0, 0, 0, 0, 0 ];
wobbuffet.setNature(Nature.MILD); wobbuffet.setNature(Nature.MILD);
wobbuffet.setAlpha(0); wobbuffet.setAlpha(0);

View File

@ -12,8 +12,7 @@ import PokemonSpecies, { allSpecies, getPokemonSpecies } from "#app/data/pokemon
import { getTypeRgb } from "#app/data/type"; import { getTypeRgb } from "#app/data/type";
import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option"; import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option";
import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode"; import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode";
import * as Utils from "#app/utils"; import { NumberHolder, isNullOrUndefined, randInt, randSeedInt, randSeedShuffle } from "#app/utils";
import { IntegerHolder, isNullOrUndefined, randInt, randSeedInt, randSeedShuffle } from "#app/utils";
import Pokemon, { EnemyPokemon, PlayerPokemon, PokemonMove } from "#app/field/pokemon"; import Pokemon, { EnemyPokemon, PlayerPokemon, PokemonMove } from "#app/field/pokemon";
import { HiddenAbilityRateBoosterModifier, PokemonFormChangeItemModifier, PokemonHeldItemModifier, ShinyRateBoosterModifier, SpeciesStatBoosterModifier } from "#app/modifier/modifier"; import { HiddenAbilityRateBoosterModifier, PokemonFormChangeItemModifier, PokemonHeldItemModifier, ShinyRateBoosterModifier, SpeciesStatBoosterModifier } from "#app/modifier/modifier";
import { OptionSelectItem } from "#app/ui/abstact-option-select-ui-handler"; import { OptionSelectItem } from "#app/ui/abstact-option-select-ui-handler";
@ -27,6 +26,7 @@ import { trainerNamePools } from "#app/data/trainer-names";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import { addPokemonDataToDexAndValidateAchievements } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { addPokemonDataToDexAndValidateAchievements } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import type { PokeballType } from "#enums/pokeball"; import type { PokeballType } from "#enums/pokeball";
import { doShinySparkleAnim } from "#app/field/anims";
/** the i18n namespace for the encounter */ /** the i18n namespace for the encounter */
const namespace = "mysteryEncounters/globalTradeSystem"; const namespace = "mysteryEncounters/globalTradeSystem";
@ -230,7 +230,7 @@ export const GlobalTradeSystemEncounter: MysteryEncounter =
const tradePokemon = new EnemyPokemon(scene, randomTradeOption, pokemon.level, TrainerSlot.NONE, false); const tradePokemon = new EnemyPokemon(scene, randomTradeOption, pokemon.level, TrainerSlot.NONE, false);
// Extra shiny roll at 1/128 odds (boosted by events and charms) // Extra shiny roll at 1/128 odds (boosted by events and charms)
if (!tradePokemon.shiny) { if (!tradePokemon.shiny) {
const shinyThreshold = new Utils.IntegerHolder(WONDER_TRADE_SHINY_CHANCE); const shinyThreshold = new NumberHolder(WONDER_TRADE_SHINY_CHANCE);
if (scene.eventManager.isEventActive()) { if (scene.eventManager.isEventActive()) {
shinyThreshold.value *= scene.eventManager.getShinyMultiplier(); shinyThreshold.value *= scene.eventManager.getShinyMultiplier();
} }
@ -247,7 +247,7 @@ export const GlobalTradeSystemEncounter: MysteryEncounter =
const hiddenIndex = tradePokemon.species.ability2 ? 2 : 1; const hiddenIndex = tradePokemon.species.ability2 ? 2 : 1;
if (tradePokemon.species.abilityHidden) { if (tradePokemon.species.abilityHidden) {
if (tradePokemon.abilityIndex < hiddenIndex) { if (tradePokemon.abilityIndex < hiddenIndex) {
const hiddenAbilityChance = new IntegerHolder(64); const hiddenAbilityChance = new NumberHolder(64);
scene.applyModifiers(HiddenAbilityRateBoosterModifier, true, hiddenAbilityChance); scene.applyModifiers(HiddenAbilityRateBoosterModifier, true, hiddenAbilityChance);
const hasHiddenAbility = !randSeedInt(hiddenAbilityChance.value); const hasHiddenAbility = !randSeedInt(hiddenAbilityChance.value);
@ -582,7 +582,13 @@ function doPokemonTradeSequence(scene: BattleScene, tradedPokemon: PlayerPokemon
receivedPokemonTintSprite.setTintFill(getPokeballTintColor(receivedPokemon.pokeball)); receivedPokemonTintSprite.setTintFill(getPokeballTintColor(receivedPokemon.pokeball));
[ tradedPokemonSprite, tradedPokemonTintSprite ].map(sprite => { [ tradedPokemonSprite, tradedPokemonTintSprite ].map(sprite => {
sprite.play(tradedPokemon.getSpriteKey(true)); const spriteKey = tradedPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(tradedPokemon.getTeraType()) }); sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(tradedPokemon.getTeraType()) });
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", tradedPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", tradedPokemon.getSpriteKey());
@ -597,7 +603,13 @@ function doPokemonTradeSequence(scene: BattleScene, tradedPokemon: PlayerPokemon
}); });
[ receivedPokemonSprite, receivedPokemonTintSprite ].map(sprite => { [ receivedPokemonSprite, receivedPokemonTintSprite ].map(sprite => {
sprite.play(receivedPokemon.getSpriteKey(true)); const spriteKey = receivedPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(tradedPokemon.getTeraType()) }); sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(tradedPokemon.getTeraType()) });
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", receivedPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", receivedPokemon.getSpriteKey());
@ -797,6 +809,14 @@ function doTradeReceivedSequence(scene: BattleScene, receivedPokemon: PlayerPoke
receivedPokeballSprite.x = tradeBaseBg.displayWidth / 2; receivedPokeballSprite.x = tradeBaseBg.displayWidth / 2;
receivedPokeballSprite.y = tradeBaseBg.displayHeight / 2 - 100; receivedPokeballSprite.y = tradeBaseBg.displayHeight / 2 - 100;
// Received pokemon sparkles
let pokemonShinySparkle: Phaser.GameObjects.Sprite;
if (receivedPokemon.shiny) {
pokemonShinySparkle = scene.add.sprite(receivedPokemonSprite.x, receivedPokemonSprite.y, "shiny");
pokemonShinySparkle.setVisible(false);
tradeContainer.add(pokemonShinySparkle);
}
const BASE_ANIM_DURATION = 1000; const BASE_ANIM_DURATION = 1000;
// Pokeball falls to the screen // Pokeball falls to the screen
@ -835,6 +855,11 @@ function doTradeReceivedSequence(scene: BattleScene, receivedPokemon: PlayerPoke
scale: 1, scale: 1,
alpha: 0, alpha: 0,
onComplete: () => { onComplete: () => {
if (receivedPokemon.shiny) {
scene.time.delayedCall(500, () => {
doShinySparkleAnim(scene, pokemonShinySparkle, receivedPokemon.variant);
});
}
receivedPokeballSprite.destroy(); receivedPokeballSprite.destroy();
scene.time.delayedCall(2000, () => resolve()); scene.time.delayedCall(2000, () => resolve());
} }

View File

@ -34,6 +34,7 @@ export const MysteriousChestEncounter: MysteryEncounter =
MysteryEncounterBuilder.withEncounterType(MysteryEncounterType.MYSTERIOUS_CHEST) MysteryEncounterBuilder.withEncounterType(MysteryEncounterType.MYSTERIOUS_CHEST)
.withEncounterTier(MysteryEncounterTier.COMMON) .withEncounterTier(MysteryEncounterTier.COMMON)
.withSceneWaveRangeRequirement(...CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES) .withSceneWaveRangeRequirement(...CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES)
.withScenePartySizeRequirement(2, 6, true)
.withAutoHideIntroVisuals(false) .withAutoHideIntroVisuals(false)
.withCatchAllowed(true) .withCatchAllowed(true)
.withIntroSpriteConfigs([ .withIntroSpriteConfigs([

View File

@ -9,9 +9,9 @@ import { EnemyPokemon } from "#app/field/pokemon";
import { PokeballType } from "#enums/pokeball"; import { PokeballType } from "#enums/pokeball";
import { PlayerGender } from "#enums/player-gender"; import { PlayerGender } from "#enums/player-gender";
import { IntegerHolder, randSeedInt } from "#app/utils"; import { IntegerHolder, randSeedInt } from "#app/utils";
import { getPokemonSpecies } from "#app/data/pokemon-species"; import PokemonSpecies, { getPokemonSpecies } from "#app/data/pokemon-species";
import { MoneyRequirement } from "#app/data/mystery-encounters/mystery-encounter-requirements"; import { MoneyRequirement } from "#app/data/mystery-encounters/mystery-encounter-requirements";
import { doPlayerFlee, doPokemonFlee, getRandomSpeciesByStarterTier, trainerThrowPokeball } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { doPlayerFlee, doPokemonFlee, getRandomSpeciesByStarterCost, trainerThrowPokeball } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import { getEncounterText, showEncounterText } from "#app/data/mystery-encounters/utils/encounter-dialogue-utils"; import { getEncounterText, showEncounterText } from "#app/data/mystery-encounters/utils/encounter-dialogue-utils";
import { getPokemonNameWithAffix } from "#app/messages"; import { getPokemonNameWithAffix } from "#app/messages";
import { MysteryEncounterTier } from "#enums/mystery-encounter-tier"; import { MysteryEncounterTier } from "#enums/mystery-encounter-tier";
@ -19,6 +19,7 @@ import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode
import { ScanIvsPhase } from "#app/phases/scan-ivs-phase"; import { ScanIvsPhase } from "#app/phases/scan-ivs-phase";
import { SummonPhase } from "#app/phases/summon-phase"; import { SummonPhase } from "#app/phases/summon-phase";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import { NON_LEGEND_PARADOX_POKEMON } from "#app/data/balance/special-species-groups";
/** the i18n namespace for the encounter */ /** the i18n namespace for the encounter */
const namespace = "mysteryEncounters/safariZone"; const namespace = "mysteryEncounters/safariZone";
@ -261,7 +262,7 @@ async function summonSafariPokemon(scene: BattleScene) {
let enemySpecies; let enemySpecies;
let pokemon; let pokemon;
scene.executeWithSeedOffset(() => { scene.executeWithSeedOffset(() => {
enemySpecies = getPokemonSpecies(getRandomSpeciesByStarterTier([ 0, 5 ], undefined, undefined, false, false, false)); enemySpecies = getSafariSpeciesSpawn();
const level = scene.currentBattle.getLevelForWave(); const level = scene.currentBattle.getLevelForWave();
enemySpecies = getPokemonSpecies(enemySpecies.getWildSpeciesForLevel(level, true, false, scene.gameMode)); enemySpecies = getPokemonSpecies(enemySpecies.getWildSpeciesForLevel(level, true, false, scene.gameMode));
pokemon = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.NONE, false); pokemon = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.NONE, false);
@ -526,3 +527,10 @@ async function doEndTurn(scene: BattleScene, cursorIndex: number) {
initSubsequentOptionSelect(scene, { overrideOptions: safariZoneGameOptions, startingCursorIndex: cursorIndex, hideDescription: true }); initSubsequentOptionSelect(scene, { overrideOptions: safariZoneGameOptions, startingCursorIndex: cursorIndex, hideDescription: true });
} }
} }
/**
* @returns A random species that has at most 5 starter cost and is not Mythical, Paradox, etc.
*/
export function getSafariSpeciesSpawn(): PokemonSpecies {
return getPokemonSpecies(getRandomSpeciesByStarterCost([ 0, 5 ], NON_LEGEND_PARADOX_POKEMON, undefined, false, false, false));
}

View File

@ -60,6 +60,7 @@ export const SlumberingSnorlaxEncounter: MysteryEncounter =
const pokemonConfig: EnemyPokemonConfig = { const pokemonConfig: EnemyPokemonConfig = {
species: bossSpecies, species: bossSpecies,
isBoss: true, isBoss: true,
shiny: false, // Shiny lock because shiny is rolled only if the battle option is picked
status: [ StatusEffect.SLEEP, 5 ], // Extra turns on timer for Snorlax's start of fight moves status: [ StatusEffect.SLEEP, 5 ], // Extra turns on timer for Snorlax's start of fight moves
moveSet: [ Moves.REST, Moves.SLEEP_TALK, Moves.CRUNCH, Moves.GIGA_IMPACT ], moveSet: [ Moves.REST, Moves.SLEEP_TALK, Moves.CRUNCH, Moves.GIGA_IMPACT ],
modifierConfigs: [ modifierConfigs: [

View File

@ -21,7 +21,6 @@ import { EggSourceType } from "#enums/egg-source-types";
import { EggTier } from "#enums/egg-type"; import { EggTier } from "#enums/egg-type";
import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option"; import { MysteryEncounterOptionBuilder } from "#app/data/mystery-encounters/mystery-encounter-option";
import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode"; import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode";
import { achvs } from "#app/system/achv";
import { modifierTypes, PokemonHeldItemModifierType } from "#app/modifier/modifier-type"; import { modifierTypes, PokemonHeldItemModifierType } from "#app/modifier/modifier-type";
import { Type } from "#enums/type"; import { Type } from "#enums/type";
import { getPokeballTintColor } from "#app/data/pokeball"; import { getPokeballTintColor } from "#app/data/pokeball";
@ -520,12 +519,6 @@ function removePokemonFromPartyAndStoreHeldItems(scene: BattleScene, encounter:
]; ];
} }
function checkAchievement(scene: BattleScene) {
if (scene.arena.biomeType === Biome.SPACE) {
scene.validateAchv(achvs.BREEDERS_IN_SPACE);
}
}
function restorePartyAndHeldItems(scene: BattleScene) { function restorePartyAndHeldItems(scene: BattleScene) {
const encounter = scene.currentBattle.mysteryEncounter!; const encounter = scene.currentBattle.mysteryEncounter!;
// Restore original party // Restore original party
@ -617,8 +610,6 @@ function onGameOver(scene: BattleScene) {
function doPostEncounterCleanup(scene: BattleScene) { function doPostEncounterCleanup(scene: BattleScene) {
const encounter = scene.currentBattle.mysteryEncounter!; const encounter = scene.currentBattle.mysteryEncounter!;
if (!encounter.misc.encounterFailed) { if (!encounter.misc.encounterFailed) {
// Give achievement if in Space biome
checkAchievement(scene);
// Give 20 friendship to the chosen pokemon // Give 20 friendship to the chosen pokemon
encounter.misc.chosenPokemon.addFriendship(FRIENDSHIP_ADDED); encounter.misc.chosenPokemon.addFriendship(FRIENDSHIP_ADDED);
restorePartyAndHeldItems(scene); restorePartyAndHeldItems(scene);

View File

@ -4,8 +4,8 @@ import { MysteryEncounterType } from "#enums/mystery-encounter-type";
import BattleScene from "#app/battle-scene"; import BattleScene from "#app/battle-scene";
import MysteryEncounter, { MysteryEncounterBuilder } from "#app/data/mystery-encounters/mystery-encounter"; import MysteryEncounter, { MysteryEncounterBuilder } from "#app/data/mystery-encounters/mystery-encounter";
import { MoneyRequirement } from "#app/data/mystery-encounters/mystery-encounter-requirements"; import { MoneyRequirement } from "#app/data/mystery-encounters/mystery-encounter-requirements";
import { catchPokemon, getRandomSpeciesByStarterTier, getSpriteKeysFromPokemon } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { catchPokemon, getRandomSpeciesByStarterCost, getSpriteKeysFromPokemon } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import { getPokemonSpecies } from "#app/data/pokemon-species"; import PokemonSpecies, { getPokemonSpecies } from "#app/data/pokemon-species";
import { speciesStarterCosts } from "#app/data/balance/starters"; import { speciesStarterCosts } from "#app/data/balance/starters";
import { Species } from "#enums/species"; import { Species } from "#enums/species";
import { PokeballType } from "#enums/pokeball"; import { PokeballType } from "#enums/pokeball";
@ -17,6 +17,7 @@ import { MysteryEncounterTier } from "#enums/mystery-encounter-tier";
import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode"; import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import { Abilities } from "#enums/abilities"; import { Abilities } from "#enums/abilities";
import { NON_LEGEND_PARADOX_POKEMON } from "#app/data/balance/special-species-groups";
/** the i18n namespace for this encounter */ /** the i18n namespace for this encounter */
const namespace = "mysteryEncounters/thePokemonSalesman"; const namespace = "mysteryEncounters/thePokemonSalesman";
@ -60,24 +61,22 @@ export const ThePokemonSalesmanEncounter: MysteryEncounter =
.withOnInit((scene: BattleScene) => { .withOnInit((scene: BattleScene) => {
const encounter = scene.currentBattle.mysteryEncounter!; const encounter = scene.currentBattle.mysteryEncounter!;
let species = getPokemonSpecies(getRandomSpeciesByStarterTier([ 0, 5 ], undefined, undefined, false, false, false)); let species = getSalesmanSpeciesOffer();
let tries = 0; let tries = 0;
// Reroll any species that don't have HAs // Reroll any species that don't have HAs
while ((isNullOrUndefined(species.abilityHidden) || species.abilityHidden === Abilities.NONE) && tries < 5) { while ((isNullOrUndefined(species.abilityHidden) || species.abilityHidden === Abilities.NONE) && tries < 5) {
species = getPokemonSpecies(getRandomSpeciesByStarterTier([ 0, 5 ], undefined, undefined, false, false, false)); species = getSalesmanSpeciesOffer();
tries++; tries++;
} }
let pokemon: PlayerPokemon; let pokemon: PlayerPokemon;
if (randSeedInt(SHINY_MAGIKARP_WEIGHT) === 0 || isNullOrUndefined(species.abilityHidden) || species.abilityHidden === Abilities.NONE) { if (randSeedInt(SHINY_MAGIKARP_WEIGHT) === 0 || isNullOrUndefined(species.abilityHidden) || species.abilityHidden === Abilities.NONE) {
// If no HA mon found or you roll 1%, give shiny Magikarp // If no HA mon found or you roll 1%, give shiny Magikarp with random variant
species = getPokemonSpecies(Species.MAGIKARP); species = getPokemonSpecies(Species.MAGIKARP);
const hiddenIndex = species.ability2 ? 2 : 1; pokemon = new PlayerPokemon(scene, species, 5, 2, species.formIndex, undefined, true);
pokemon = new PlayerPokemon(scene, species, 5, hiddenIndex, species.formIndex, undefined, true, 0);
} else { } else {
const hiddenIndex = species.ability2 ? 2 : 1; pokemon = new PlayerPokemon(scene, species, 5, 2, species.formIndex);
pokemon = new PlayerPokemon(scene, species, 5, hiddenIndex, species.formIndex);
} }
pokemon.generateAndPopulateMoveset(); pokemon.generateAndPopulateMoveset();
@ -87,7 +86,9 @@ export const ThePokemonSalesmanEncounter: MysteryEncounter =
fileRoot: fileRoot, fileRoot: fileRoot,
hasShadow: true, hasShadow: true,
repeat: true, repeat: true,
isPokemon: true isPokemon: true,
isShiny: pokemon.shiny,
variant: pokemon.variant
}); });
const starterTier = speciesStarterCosts[species.speciesId]; const starterTier = speciesStarterCosts[species.speciesId];
@ -164,3 +165,10 @@ export const ThePokemonSalesmanEncounter: MysteryEncounter =
} }
) )
.build(); .build();
/**
* @returns A random species that has at most 5 starter cost and is not Mythical, Paradox, etc.
*/
export function getSalesmanSpeciesOffer(): PokemonSpecies {
return getPokemonSpecies(getRandomSpeciesByStarterCost([ 0, 5 ], NON_LEGEND_PARADOX_POKEMON, undefined, false, false, false));
}

View File

@ -79,6 +79,7 @@ export const TheStrongStuffEncounter: MysteryEncounter =
species: getPokemonSpecies(Species.SHUCKLE), species: getPokemonSpecies(Species.SHUCKLE),
isBoss: true, isBoss: true,
bossSegments: 5, bossSegments: 5,
shiny: false, // Shiny lock because shiny is rolled only if the battle option is picked
customPokemonData: new CustomPokemonData({ spriteScale: 1.25 }), customPokemonData: new CustomPokemonData({ spriteScale: 1.25 }),
nature: Nature.BOLD, nature: Nature.BOLD,
moveSet: [ Moves.INFESTATION, Moves.SALT_CURE, Moves.GASTRO_ACID, Moves.HEAL_ORDER ], moveSet: [ Moves.INFESTATION, Moves.SALT_CURE, Moves.GASTRO_ACID, Moves.HEAL_ORDER ],

View File

@ -61,11 +61,12 @@ export const TrashToTreasureEncounter: MysteryEncounter =
.withOnInit((scene: BattleScene) => { .withOnInit((scene: BattleScene) => {
const encounter = scene.currentBattle.mysteryEncounter!; const encounter = scene.currentBattle.mysteryEncounter!;
// Calculate boss mon // Calculate boss mon (shiny locked)
const bossSpecies = getPokemonSpecies(Species.GARBODOR); const bossSpecies = getPokemonSpecies(Species.GARBODOR);
const pokemonConfig: EnemyPokemonConfig = { const pokemonConfig: EnemyPokemonConfig = {
species: bossSpecies, species: bossSpecies,
isBoss: true, isBoss: true,
shiny: false, // Shiny lock because of custom intro sprite
formIndex: 1, // Gmax formIndex: 1, // Gmax
bossSegmentModifier: 1, // +1 Segment from normal bossSegmentModifier: 1, // +1 Segment from normal
moveSet: [ Moves.PAYBACK, Moves.GUNK_SHOT, Moves.STOMPING_TANTRUM, Moves.DRAIN_PUNCH ] moveSet: [ Moves.PAYBACK, Moves.GUNK_SHOT, Moves.STOMPING_TANTRUM, Moves.DRAIN_PUNCH ]

View File

@ -12,7 +12,7 @@ import { MysteryEncounterOptionMode } from "#enums/mystery-encounter-option-mode
import { TrainerSlot } from "#app/data/trainer-config"; import { TrainerSlot } from "#app/data/trainer-config";
import { catchPokemon, getHighestLevelPlayerPokemon, getSpriteKeysFromPokemon } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { catchPokemon, getHighestLevelPlayerPokemon, getSpriteKeysFromPokemon } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import PokemonData from "#app/system/pokemon-data"; import PokemonData from "#app/system/pokemon-data";
import { isNullOrUndefined, randSeedInt } from "#app/utils"; import { isNullOrUndefined, randSeedInt, randSeedItem } from "#app/utils";
import { Moves } from "#enums/moves"; import { Moves } from "#enums/moves";
import { BattlerIndex } from "#app/battle"; import { BattlerIndex } from "#app/battle";
import { SelfStatusMove } from "#app/data/move"; import { SelfStatusMove } from "#app/data/move";
@ -23,6 +23,7 @@ import { BerryModifier } from "#app/modifier/modifier";
import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase"; import { StatStageChangePhase } from "#app/phases/stat-stage-change-phase";
import { Stat } from "#enums/stat"; import { Stat } from "#enums/stat";
import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode"; import { CLASSIC_MODE_MYSTERY_ENCOUNTER_WAVES } from "#app/game-mode";
import PokemonSpecies, { getPokemonSpecies } from "#app/data/pokemon-species";
/** the i18n namespace for the encounter */ /** the i18n namespace for the encounter */
const namespace = "mysteryEncounters/uncommonBreed"; const namespace = "mysteryEncounters/uncommonBreed";
@ -51,7 +52,14 @@ export const UncommonBreedEncounter: MysteryEncounter =
// Calculate boss mon // Calculate boss mon
// Level equal to 2 below highest party member // Level equal to 2 below highest party member
const level = getHighestLevelPlayerPokemon(scene, false, true).level - 2; const level = getHighestLevelPlayerPokemon(scene, false, true).level - 2;
const species = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true); let species: PokemonSpecies;
if (scene.eventManager.isEventActive() && scene.eventManager.activeEvent()?.uncommonBreedEncounters && randSeedInt(2) === 1) {
const eventEncounter = randSeedItem(scene.eventManager.activeEvent()!.uncommonBreedEncounters!);
const levelSpecies = getPokemonSpecies(eventEncounter.species).getWildSpeciesForLevel(level, eventEncounter.allowEvolution ?? false, true, scene.gameMode);
species = getPokemonSpecies( levelSpecies );
} else {
species = scene.arena.randomSpecies(scene.currentBattle.waveIndex, level, 0, getPartyLuckValue(scene.getPlayerParty()), true);
}
const pokemon = new EnemyPokemon(scene, species, level, TrainerSlot.NONE, true); const pokemon = new EnemyPokemon(scene, species, level, TrainerSlot.NONE, true);
// Pokemon will always have one of its egg moves in its moveset // Pokemon will always have one of its egg moves in its moveset
@ -100,7 +108,9 @@ export const UncommonBreedEncounter: MysteryEncounter =
hasShadow: true, hasShadow: true,
x: -5, x: -5,
repeat: true, repeat: true,
isPokemon: true isPokemon: true,
isShiny: pokemon.shiny,
variant: pokemon.variant
}, },
]; ];
@ -113,13 +123,15 @@ export const UncommonBreedEncounter: MysteryEncounter =
const encounter = scene.currentBattle.mysteryEncounter!; const encounter = scene.currentBattle.mysteryEncounter!;
const pokemonSprite = encounter.introVisuals!.getSprites(); const pokemonSprite = encounter.introVisuals!.getSprites();
scene.tweens.add({ // Bounce at the end // Bounce at the end, then shiny sparkle if the Pokemon is shiny
scene.tweens.add({
targets: pokemonSprite, targets: pokemonSprite,
duration: 300, duration: 300,
ease: "Cubic.easeOut", ease: "Cubic.easeOut",
yoyo: true, yoyo: true,
y: "-=20", y: "-=20",
loop: 1, loop: 1,
onComplete: () => encounter.introVisuals?.playShinySparkles()
}); });
scene.time.delayedCall(500, () => scene.playSound("battle_anims/PRSFX- Spotlight2")); scene.time.delayedCall(500, () => scene.playSound("battle_anims/PRSFX- Spotlight2"));

View File

@ -177,7 +177,7 @@ export const allMysteryEncounters: { [encounterType: number]: MysteryEncounter }
const extremeBiomeEncounters: MysteryEncounterType[] = []; const extremeBiomeEncounters: MysteryEncounterType[] = [];
const nonExtremeBiomeEncounters: MysteryEncounterType[] = [ const nonExtremeBiomeEncounters: MysteryEncounterType[] = [
MysteryEncounterType.FIELD_TRIP, // MysteryEncounterType.FIELD_TRIP, Disabled for holiday event
MysteryEncounterType.DANCING_LESSONS, // Is also in BADLANDS, DESERT, VOLCANO, WASTELAND, ABYSS MysteryEncounterType.DANCING_LESSONS, // Is also in BADLANDS, DESERT, VOLCANO, WASTELAND, ABYSS
]; ];
@ -185,14 +185,14 @@ const humanTransitableBiomeEncounters: MysteryEncounterType[] = [
MysteryEncounterType.MYSTERIOUS_CHALLENGERS, MysteryEncounterType.MYSTERIOUS_CHALLENGERS,
MysteryEncounterType.SHADY_VITAMIN_DEALER, MysteryEncounterType.SHADY_VITAMIN_DEALER,
MysteryEncounterType.THE_POKEMON_SALESMAN, MysteryEncounterType.THE_POKEMON_SALESMAN,
MysteryEncounterType.AN_OFFER_YOU_CANT_REFUSE, // MysteryEncounterType.AN_OFFER_YOU_CANT_REFUSE, Disabled for holiday event
MysteryEncounterType.THE_WINSTRATE_CHALLENGE, MysteryEncounterType.THE_WINSTRATE_CHALLENGE,
MysteryEncounterType.THE_EXPERT_POKEMON_BREEDER MysteryEncounterType.THE_EXPERT_POKEMON_BREEDER
]; ];
const civilizationBiomeEncounters: MysteryEncounterType[] = [ const civilizationBiomeEncounters: MysteryEncounterType[] = [
MysteryEncounterType.DEPARTMENT_STORE_SALE, // MysteryEncounterType.DEPARTMENT_STORE_SALE, Disabled for holiday event
MysteryEncounterType.PART_TIMER, // MysteryEncounterType.PART_TIMER, Disabled for holiday event
MysteryEncounterType.FUN_AND_GAMES, MysteryEncounterType.FUN_AND_GAMES,
MysteryEncounterType.GLOBAL_TRADE_SYSTEM MysteryEncounterType.GLOBAL_TRADE_SYSTEM
]; ];

View File

@ -184,7 +184,7 @@ export async function initBattleWithEnemyConfig(scene: BattleScene, partyConfig:
dataSource = config.dataSource; dataSource = config.dataSource;
enemySpecies = config.species; enemySpecies = config.species;
isBoss = config.isBoss; isBoss = config.isBoss;
battle.enemyParty[e] = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.TRAINER, isBoss, dataSource); battle.enemyParty[e] = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.TRAINER, isBoss, false, dataSource);
} else { } else {
battle.enemyParty[e] = battle.trainer.genPartyMember(e); battle.enemyParty[e] = battle.trainer.genPartyMember(e);
} }
@ -202,7 +202,7 @@ export async function initBattleWithEnemyConfig(scene: BattleScene, partyConfig:
enemySpecies = scene.randomSpecies(battle.waveIndex, level, true); enemySpecies = scene.randomSpecies(battle.waveIndex, level, true);
} }
battle.enemyParty[e] = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.NONE, isBoss, dataSource); battle.enemyParty[e] = scene.addEnemyPokemon(enemySpecies, level, TrainerSlot.NONE, isBoss, false, dataSource);
} }
} }
@ -731,7 +731,7 @@ export function handleMysteryEncounterVictory(scene: BattleScene, addHealPhase:
scene.pushPhase(new MysteryEncounterRewardsPhase(scene, addHealPhase)); scene.pushPhase(new MysteryEncounterRewardsPhase(scene, addHealPhase));
scene.pushPhase(new EggLapsePhase(scene)); scene.pushPhase(new EggLapsePhase(scene));
} else if (!scene.getEnemyParty().find(p => encounter.encounterMode !== MysteryEncounterMode.TRAINER_BATTLE ? p.isOnField() : !p?.isFainted(true))) { } else if (!scene.getEnemyParty().find(p => encounter.encounterMode !== MysteryEncounterMode.TRAINER_BATTLE ? p.isOnField() : !p?.isFainted(true))) {
scene.pushPhase(new BattleEndPhase(scene)); scene.pushPhase(new BattleEndPhase(scene, true));
if (encounter.encounterMode === MysteryEncounterMode.TRAINER_BATTLE) { if (encounter.encounterMode === MysteryEncounterMode.TRAINER_BATTLE) {
scene.pushPhase(new TrainerVictoryPhase(scene)); scene.pushPhase(new TrainerVictoryPhase(scene));
} }

View File

@ -207,7 +207,7 @@ export function getHighestStatTotalPlayerPokemon(scene: BattleScene, isAllowed:
* @param allowMythical * @param allowMythical
* @returns * @returns
*/ */
export function getRandomSpeciesByStarterTier(starterTiers: number | [number, number], excludedSpecies?: Species[], types?: Type[], allowSubLegendary: boolean = true, allowLegendary: boolean = true, allowMythical: boolean = true): Species { export function getRandomSpeciesByStarterCost(starterTiers: number | [number, number], excludedSpecies?: Species[], types?: Type[], allowSubLegendary: boolean = true, allowLegendary: boolean = true, allowMythical: boolean = true): Species {
let min = Array.isArray(starterTiers) ? starterTiers[0] : starterTiers; let min = Array.isArray(starterTiers) ? starterTiers[0] : starterTiers;
let max = Array.isArray(starterTiers) ? starterTiers[1] : starterTiers; let max = Array.isArray(starterTiers) ? starterTiers[1] : starterTiers;
@ -290,7 +290,10 @@ export function applyDamageToPokemon(scene: BattleScene, pokemon: PlayerPokemon,
if (damage <= 0) { if (damage <= 0) {
console.warn("Healing pokemon with `applyDamageToPokemon` is not recommended! Please use `applyHealToPokemon` instead."); console.warn("Healing pokemon with `applyDamageToPokemon` is not recommended! Please use `applyHealToPokemon` instead.");
} }
// If a Pokemon would faint from the damage applied, its HP is instead set to 1.
if (pokemon.isAllowedInBattle() && pokemon.hp - damage <= 0) {
damage = pokemon.hp - 1;
}
applyHpChangeToPokemon(scene, pokemon, -damage); applyHpChangeToPokemon(scene, pokemon, -damage);
} }

View File

@ -54,7 +54,13 @@ export function doPokemonTransformationSequence(scene: BattleScene, previousPoke
pokemonEvoTintSprite.setTintFill(0xFFFFFF); pokemonEvoTintSprite.setTintFill(0xFFFFFF);
[ pokemonSprite, pokemonTintSprite, pokemonEvoSprite, pokemonEvoTintSprite ].map(sprite => { [ pokemonSprite, pokemonTintSprite, pokemonEvoSprite, pokemonEvoTintSprite ].map(sprite => {
sprite.play(previousPokemon.getSpriteKey(true)); const spriteKey = previousPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(previousPokemon.getTeraType()) }); sprite.setPipeline(scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(previousPokemon.getTeraType()) });
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", previousPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", previousPokemon.getSpriteKey());
@ -69,7 +75,13 @@ export function doPokemonTransformationSequence(scene: BattleScene, previousPoke
}); });
[ pokemonEvoSprite, pokemonEvoTintSprite ].map(sprite => { [ pokemonEvoSprite, pokemonEvoTintSprite ].map(sprite => {
sprite.play(transformPokemon.getSpriteKey(true)); const spriteKey = transformPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", transformPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", transformPokemon.getSpriteKey());
sprite.setPipelineData("shiny", transformPokemon.shiny); sprite.setPipelineData("shiny", transformPokemon.shiny);

View File

@ -351,6 +351,10 @@ export class MeloettaFormChangePostMoveTrigger extends SpeciesFormChangePostMove
if (pokemon.scene.gameMode.hasChallenge(Challenges.SINGLE_TYPE)) { if (pokemon.scene.gameMode.hasChallenge(Challenges.SINGLE_TYPE)) {
return false; return false;
} else { } else {
// Meloetta will not transform if it has the ability Sheer Force when using Relic Song
if (pokemon.hasAbility(Abilities.SHEER_FORCE)) {
return false;
}
return super.canChange(pokemon); return super.canChange(pokemon);
} }
} }

View File

@ -15,7 +15,7 @@ import { EvolutionLevel, SpeciesWildEvolutionDelay, pokemonEvolutions, pokemonPr
import { Type } from "#enums/type"; import { Type } from "#enums/type";
import { LevelMoves, pokemonFormLevelMoves, pokemonFormLevelMoves as pokemonSpeciesFormLevelMoves, pokemonSpeciesLevelMoves } from "#app/data/balance/pokemon-level-moves"; import { LevelMoves, pokemonFormLevelMoves, pokemonFormLevelMoves as pokemonSpeciesFormLevelMoves, pokemonSpeciesLevelMoves } from "#app/data/balance/pokemon-level-moves";
import { Stat } from "#enums/stat"; import { Stat } from "#enums/stat";
import { Variant, VariantSet, variantColorCache, variantData } from "#app/data/variant"; import { Variant, VariantSet, variantData } from "#app/data/variant";
import { speciesStarterCosts, POKERUS_STARTER_COUNT } from "#app/data/balance/starters"; import { speciesStarterCosts, POKERUS_STARTER_COUNT } from "#app/data/balance/starters";
import { SpeciesFormKey } from "#enums/species-form-key"; import { SpeciesFormKey } from "#enums/species-form-key";
@ -511,29 +511,8 @@ export abstract class PokemonSpeciesForm {
} else { } else {
scene.anims.get(spriteKey).frameRate = 10; scene.anims.get(spriteKey).frameRate = 10;
} }
let spritePath = this.getSpriteAtlasPath(female, formIndex, shiny, variant).replace("variant/", "").replace(/_[1-3]$/, ""); const spritePath = this.getSpriteAtlasPath(female, formIndex, shiny, variant).replace("variant/", "").replace(/_[1-3]$/, "");
const useExpSprite = scene.experimentalSprites && scene.hasExpSprite(spriteKey); scene.loadPokemonVariantAssets(spriteKey, spritePath, variant);
if (useExpSprite) {
spritePath = `exp/${spritePath}`;
}
let config = variantData;
spritePath.split("/").map(p => config ? config = config[p] : null);
const variantSet = config as VariantSet;
if (variantSet && (variant !== undefined && variantSet[variant] === 1)) {
const populateVariantColors = (key: string): Promise<void> => {
return new Promise(resolve => {
if (variantColorCache.hasOwnProperty(key)) {
return resolve();
}
scene.cachedFetch(`./images/pokemon/variant/${spritePath}.json`).then(res => res.json()).then(c => {
variantColorCache[key] = c;
resolve();
});
});
};
populateVariantColors(spriteKey).then(() => resolve());
return;
}
resolve(); resolve();
}); });
if (startLoad) { if (startLoad) {

View File

@ -1170,19 +1170,34 @@ function getGymLeaderPartyTemplate(scene: BattleScene) {
export function getRandomPartyMemberFunc(speciesPool: Species[], trainerSlot: TrainerSlot = TrainerSlot.TRAINER, ignoreEvolution: boolean = false, postProcess?: (enemyPokemon: EnemyPokemon) => void) { export function getRandomPartyMemberFunc(speciesPool: Species[], trainerSlot: TrainerSlot = TrainerSlot.TRAINER, ignoreEvolution: boolean = false, postProcess?: (enemyPokemon: EnemyPokemon) => void) {
return (scene: BattleScene, level: number, strength: PartyMemberStrength) => { return (scene: BattleScene, level: number, strength: PartyMemberStrength) => {
let species = Utils.randSeedItem(speciesPool); let species = Utils.randSeedItem(speciesPool);
if (scene.gameMode.isClassic && scene.currentBattle.waveIndex === 20) {
ignoreEvolution = true;
}
if (!ignoreEvolution) { if (!ignoreEvolution) {
species = getPokemonSpecies(species).getTrainerSpeciesForLevel(level, true, strength, scene.currentBattle.waveIndex); species = getPokemonSpecies(species).getTrainerSpeciesForLevel(level, true, strength, scene.currentBattle.waveIndex);
} }
return scene.addEnemyPokemon(getPokemonSpecies(species), level, trainerSlot, undefined, undefined, postProcess); return scene.addEnemyPokemon(getPokemonSpecies(species), level, trainerSlot, undefined, false, undefined, postProcess);
}; };
} }
function getSpeciesFilterRandomPartyMemberFunc(speciesFilter: PokemonSpeciesFilter, trainerSlot: TrainerSlot = TrainerSlot.TRAINER, allowLegendaries?: boolean, postProcess?: (EnemyPokemon: EnemyPokemon) => void): PartyMemberFunc { function getSpeciesFilterRandomPartyMemberFunc(
const originalSpeciesFilter = speciesFilter; originalSpeciesFilter: PokemonSpeciesFilter,
speciesFilter = (species: PokemonSpecies) => (allowLegendaries || (!species.legendary && !species.subLegendary && !species.mythical)) && !species.isTrainerForbidden() && originalSpeciesFilter(species); trainerSlot: TrainerSlot = TrainerSlot.TRAINER,
return (scene: BattleScene, level: integer, strength: PartyMemberStrength) => { allowLegendaries?: boolean,
const ret = scene.addEnemyPokemon(getPokemonSpecies(scene.randomSpecies(scene.currentBattle.waveIndex, level, false, speciesFilter).getTrainerSpeciesForLevel(level, true, strength, scene.currentBattle.waveIndex)), level, trainerSlot, undefined, undefined, postProcess); postProcess?: (EnemyPokemon: EnemyPokemon) => void
return ret; ): PartyMemberFunc {
const speciesFilter = (species: PokemonSpecies): boolean => {
const notLegendary = !species.legendary && !species.subLegendary && !species.mythical;
return (allowLegendaries || notLegendary) && !species.isTrainerForbidden() && originalSpeciesFilter(species);
};
return (scene: BattleScene, level: number, strength: PartyMemberStrength) => {
const waveIndex = scene.currentBattle.waveIndex;
const species = getPokemonSpecies(scene.randomSpecies(waveIndex, level, false, speciesFilter)
.getTrainerSpeciesForLevel(level, true, strength, waveIndex));
return scene.addEnemyPokemon(species, level, trainerSlot, undefined, false, undefined, postProcess);
}; };
} }
@ -1217,7 +1232,7 @@ export const signatureSpecies: SignatureSpecies = {
GIOVANNI: [ Species.SANDILE, Species.MURKROW, Species.NIDORAN_M, Species.NIDORAN_F ], GIOVANNI: [ Species.SANDILE, Species.MURKROW, Species.NIDORAN_M, Species.NIDORAN_F ],
FALKNER: [ Species.PIDGEY, Species.HOOTHOOT, Species.DODUO ], FALKNER: [ Species.PIDGEY, Species.HOOTHOOT, Species.DODUO ],
BUGSY: [ Species.SCYTHER, Species.HERACROSS, Species.SHUCKLE, Species.PINSIR ], BUGSY: [ Species.SCYTHER, Species.HERACROSS, Species.SHUCKLE, Species.PINSIR ],
WHITNEY: [ Species.GIRAFARIG, Species.MILTANK ], WHITNEY: [ Species.JIGGLYPUFF, Species.MILTANK, Species.AIPOM, Species.GIRAFARIG ],
MORTY: [ Species.GASTLY, Species.MISDREAVUS, Species.SABLEYE ], MORTY: [ Species.GASTLY, Species.MISDREAVUS, Species.SABLEYE ],
CHUCK: [ Species.POLIWRATH, Species.MANKEY ], CHUCK: [ Species.POLIWRATH, Species.MANKEY ],
JASMINE: [ Species.MAGNEMITE, Species.STEELIX ], JASMINE: [ Species.MAGNEMITE, Species.STEELIX ],
@ -1227,7 +1242,7 @@ export const signatureSpecies: SignatureSpecies = {
BRAWLY: [ Species.MACHOP, Species.MAKUHITA ], BRAWLY: [ Species.MACHOP, Species.MAKUHITA ],
WATTSON: [ Species.MAGNEMITE, Species.VOLTORB, Species.ELECTRIKE ], WATTSON: [ Species.MAGNEMITE, Species.VOLTORB, Species.ELECTRIKE ],
FLANNERY: [ Species.SLUGMA, Species.TORKOAL, Species.NUMEL ], FLANNERY: [ Species.SLUGMA, Species.TORKOAL, Species.NUMEL ],
NORMAN: [ Species.SLAKOTH, Species.SPINDA, Species.CHANSEY, Species.KANGASKHAN ], NORMAN: [ Species.SLAKOTH, Species.SPINDA, Species.ZIGZAGOON, Species.KECLEON ],
WINONA: [ Species.SWABLU, Species.WINGULL, Species.TROPIUS, Species.SKARMORY ], WINONA: [ Species.SWABLU, Species.WINGULL, Species.TROPIUS, Species.SKARMORY ],
TATE: [ Species.SOLROCK, Species.NATU, Species.CHIMECHO, Species.GALLADE ], TATE: [ Species.SOLROCK, Species.NATU, Species.CHIMECHO, Species.GALLADE ],
LIZA: [ Species.LUNATONE, Species.SPOINK, Species.BALTOY, Species.GARDEVOIR ], LIZA: [ Species.LUNATONE, Species.SPOINK, Species.BALTOY, Species.GARDEVOIR ],
@ -1235,16 +1250,16 @@ export const signatureSpecies: SignatureSpecies = {
ROARK: [ Species.CRANIDOS, Species.LARVITAR, Species.GEODUDE ], ROARK: [ Species.CRANIDOS, Species.LARVITAR, Species.GEODUDE ],
GARDENIA: [ Species.ROSELIA, Species.TANGELA, Species.TURTWIG ], GARDENIA: [ Species.ROSELIA, Species.TANGELA, Species.TURTWIG ],
MAYLENE: [ Species.LUCARIO, Species.MEDITITE, Species.CHIMCHAR ], MAYLENE: [ Species.LUCARIO, Species.MEDITITE, Species.CHIMCHAR ],
CRASHER_WAKE: [ Species.BUIZEL, Species.MAGIKARP, Species.PIPLUP ], CRASHER_WAKE: [ Species.BUIZEL, Species.WOOPER, Species.PIPLUP, Species.MAGIKARP ],
FANTINA: [ Species.MISDREAVUS, Species.DRIFLOON, Species.SPIRITOMB ], FANTINA: [ Species.MISDREAVUS, Species.DRIFLOON, Species.SPIRITOMB ],
BYRON: [ Species.SHIELDON, Species.BRONZOR, Species.AGGRON ], BYRON: [ Species.SHIELDON, Species.BRONZOR, Species.AGGRON ],
CANDICE: [ Species.SNEASEL, Species.SNOVER, Species.SNORUNT ], CANDICE: [ Species.SNEASEL, Species.SNOVER, Species.SNORUNT ],
VOLKNER: [ Species.SHINX, Species.CHINCHOU, Species.ROTOM ], VOLKNER: [ Species.SHINX, Species.CHINCHOU, Species.ROTOM ],
CILAN: [ Species.PANSAGE, Species.COTTONEE, Species.PETILIL ], CILAN: [ Species.PANSAGE, Species.FOONGUS, Species.PETILIL ],
CHILI: [ Species.PANSEAR, Species.DARUMAKA, Species.HEATMOR ], CHILI: [ Species.PANSEAR, Species.DARUMAKA, Species.NUMEL ],
CRESS: [ Species.PANPOUR, Species.BASCULIN, Species.TYMPOLE ], CRESS: [ Species.PANPOUR, Species.TYMPOLE, Species.SLOWPOKE ],
CHEREN: [ Species.LILLIPUP, Species.MINCCINO, Species.PATRAT ], CHEREN: [ Species.LILLIPUP, Species.MINCCINO, Species.PIDOVE ],
LENORA: [ Species.KANGASKHAN, Species.DEERLING, Species.AUDINO ], LENORA: [ Species.PATRAT, Species.DEERLING, Species.AUDINO ],
ROXIE: [ Species.VENIPEDE, Species.TRUBBISH, Species.SKORUPI ], ROXIE: [ Species.VENIPEDE, Species.TRUBBISH, Species.SKORUPI ],
BURGH: [ Species.SEWADDLE, Species.SHELMET, Species.KARRABLAST ], BURGH: [ Species.SEWADDLE, Species.SHELMET, Species.KARRABLAST ],
ELESA: [ Species.EMOLGA, Species.BLITZLE, Species.JOLTIK ], ELESA: [ Species.EMOLGA, Species.BLITZLE, Species.JOLTIK ],
@ -1277,7 +1292,7 @@ export const signatureSpecies: SignatureSpecies = {
BRASSIUS: [ Species.SMOLIV, Species.SHROOMISH, Species.ODDISH ], BRASSIUS: [ Species.SMOLIV, Species.SHROOMISH, Species.ODDISH ],
IONO: [ Species.TADBULB, Species.WATTREL, Species.VOLTORB ], IONO: [ Species.TADBULB, Species.WATTREL, Species.VOLTORB ],
KOFU: [ Species.VELUZA, Species.WIGLETT, Species.WINGULL ], KOFU: [ Species.VELUZA, Species.WIGLETT, Species.WINGULL ],
LARRY: [ Species.STARLY, Species.DUNSPARCE, Species.KOMALA ], LARRY: [ Species.STARLY, Species.DUNSPARCE, Species.LECHONK, Species.KOMALA ],
RYME: [ Species.GREAVARD, Species.SHUPPET, Species.MIMIKYU ], RYME: [ Species.GREAVARD, Species.SHUPPET, Species.MIMIKYU ],
TULIP: [ Species.GIRAFARIG, Species.FLITTLE, Species.RALTS ], TULIP: [ Species.GIRAFARIG, Species.FLITTLE, Species.RALTS ],
GRUSHA: [ Species.CETODDLE, Species.ALOLA_VULPIX, Species.CUBCHOO ], GRUSHA: [ Species.CETODDLE, Species.ALOLA_VULPIX, Species.CUBCHOO ],
@ -1840,7 +1855,7 @@ export const trainerConfigs: TrainerConfigs = {
[TrainerType.RIVAL]: new TrainerConfig((t = TrainerType.RIVAL)).setName("Finn").setHasGenders("Ivy").setHasCharSprite().setTitle("Rival").setStaticParty().setEncounterBgm(TrainerType.RIVAL).setBattleBgm("battle_rival").setMixedBattleBgm("battle_rival").setPartyTemplates(trainerPartyTemplates.RIVAL) [TrainerType.RIVAL]: new TrainerConfig((t = TrainerType.RIVAL)).setName("Finn").setHasGenders("Ivy").setHasCharSprite().setTitle("Rival").setStaticParty().setEncounterBgm(TrainerType.RIVAL).setBattleBgm("battle_rival").setMixedBattleBgm("battle_rival").setPartyTemplates(trainerPartyTemplates.RIVAL)
.setModifierRewardFuncs(() => modifierTypes.SUPER_EXP_CHARM, () => modifierTypes.EXP_SHARE) .setModifierRewardFuncs(() => modifierTypes.SUPER_EXP_CHARM, () => modifierTypes.EXP_SHARE)
.setEventModifierRewardFuncs(() => modifierTypes.SHINY_CHARM, () => modifierTypes.ABILITY_CHARM) .setEventModifierRewardFuncs(() => modifierTypes.SHINY_CHARM, () => modifierTypes.ABILITY_CHARM, () => modifierTypes.CATCHING_CHARM)
.setPartyMemberFunc(0, getRandomPartyMemberFunc([ Species.BULBASAUR, Species.CHARMANDER, Species.SQUIRTLE, Species.CHIKORITA, Species.CYNDAQUIL, Species.TOTODILE, Species.TREECKO, Species.TORCHIC, Species.MUDKIP, Species.TURTWIG, Species.CHIMCHAR, Species.PIPLUP, Species.SNIVY, Species.TEPIG, Species.OSHAWOTT, Species.CHESPIN, Species.FENNEKIN, Species.FROAKIE, Species.ROWLET, Species.LITTEN, Species.POPPLIO, Species.GROOKEY, Species.SCORBUNNY, Species.SOBBLE, Species.SPRIGATITO, Species.FUECOCO, Species.QUAXLY ], TrainerSlot.TRAINER, true, .setPartyMemberFunc(0, getRandomPartyMemberFunc([ Species.BULBASAUR, Species.CHARMANDER, Species.SQUIRTLE, Species.CHIKORITA, Species.CYNDAQUIL, Species.TOTODILE, Species.TREECKO, Species.TORCHIC, Species.MUDKIP, Species.TURTWIG, Species.CHIMCHAR, Species.PIPLUP, Species.SNIVY, Species.TEPIG, Species.OSHAWOTT, Species.CHESPIN, Species.FENNEKIN, Species.FROAKIE, Species.ROWLET, Species.LITTEN, Species.POPPLIO, Species.GROOKEY, Species.SCORBUNNY, Species.SOBBLE, Species.SPRIGATITO, Species.FUECOCO, Species.QUAXLY ], TrainerSlot.TRAINER, true,
(p => p.abilityIndex = 0))) (p => p.abilityIndex = 0)))
.setPartyMemberFunc(1, getRandomPartyMemberFunc([ Species.PIDGEY, Species.HOOTHOOT, Species.TAILLOW, Species.STARLY, Species.PIDOVE, Species.FLETCHLING, Species.PIKIPEK, Species.ROOKIDEE, Species.WATTREL ], TrainerSlot.TRAINER, true)), .setPartyMemberFunc(1, getRandomPartyMemberFunc([ Species.PIDGEY, Species.HOOTHOOT, Species.TAILLOW, Species.STARLY, Species.PIDOVE, Species.FLETCHLING, Species.PIKIPEK, Species.ROOKIDEE, Species.WATTREL ], TrainerSlot.TRAINER, true)),

View File

@ -242,7 +242,7 @@ export function getTerrainBlockMessage(pokemon: Pokemon, terrainType: TerrainTyp
return i18next.t("terrain:defaultBlockMessage", { pokemonNameWithAffix: getPokemonNameWithAffix(pokemon), terrainName: getTerrainName(terrainType) }); return i18next.t("terrain:defaultBlockMessage", { pokemonNameWithAffix: getPokemonNameWithAffix(pokemon), terrainName: getTerrainName(terrainType) });
} }
interface WeatherPoolEntry { export interface WeatherPoolEntry {
weatherType: WeatherType; weatherType: WeatherType;
weight: integer; weight: integer;
} }
@ -373,6 +373,10 @@ export function getRandomWeatherType(arena: any /* Importing from arena causes a
break; break;
} }
if (arena.biomeType === Biome.TOWN && arena.scene.eventManager.isEventActive() && arena.scene.eventManager.activeEvent()?.weather?.length > 0) {
arena.scene.eventManager.activeEvent().weather.map(w => weatherPool.push(w));
}
if (weatherPool.length > 1) { if (weatherPool.length > 1) {
let totalWeight = 0; let totalWeight = 0;
weatherPool.forEach(w => totalWeight += w.weight); weatherPool.forEach(w => totalWeight += w.weight);

View File

@ -93,4 +93,5 @@ export enum BattlerTagType {
GRUDGE = "GRUDGE", GRUDGE = "GRUDGE",
PSYCHO_SHIFT = "PSYCHO_SHIFT", PSYCHO_SHIFT = "PSYCHO_SHIFT",
ENDURE_TOKEN = "ENDURE_TOKEN", ENDURE_TOKEN = "ENDURE_TOKEN",
POWDER = "POWDER",
} }

View File

@ -10,5 +10,7 @@ export enum SwitchType {
/** Transfers stat stages and other effects from the returning Pokemon to the switched in Pokemon */ /** Transfers stat stages and other effects from the returning Pokemon to the switched in Pokemon */
BATON_PASS, BATON_PASS,
/** Transfers the returning Pokemon's Substitute to the switched in Pokemon */ /** Transfers the returning Pokemon's Substitute to the switched in Pokemon */
SHED_TAIL SHED_TAIL,
/** Force switchout to a random party member */
FORCE_SWITCH,
} }

View File

@ -1,6 +1,7 @@
import BattleScene from "../battle-scene"; import BattleScene from "#app/battle-scene";
import { PokeballType } from "#enums/pokeball"; import { PokeballType } from "#enums/pokeball";
import * as Utils from "../utils"; import { Variant } from "#app/data/variant";
import { getFrameMs, randGauss } from "#app/utils";
export function addPokeballOpenParticles(scene: BattleScene, x: number, y: number, pokeballType: PokeballType): void { export function addPokeballOpenParticles(scene: BattleScene, x: number, y: number, pokeballType: PokeballType): void {
switch (pokeballType) { switch (pokeballType) {
@ -127,7 +128,7 @@ function doFanOutParticle(scene: BattleScene, trigIndex: integer, x: integer, y:
const particleTimer = scene.tweens.addCounter({ const particleTimer = scene.tweens.addCounter({
repeat: -1, repeat: -1,
duration: Utils.getFrameMs(1), duration: getFrameMs(1),
onRepeat: () => { onRepeat: () => {
updateParticle(); updateParticle();
} }
@ -159,7 +160,7 @@ export function addPokeballCaptureStars(scene: BattleScene, pokeball: Phaser.Gam
} }
}); });
const dist = Utils.randGauss(25); const dist = randGauss(25);
scene.tweens.add({ scene.tweens.add({
targets: particle, targets: particle,
x: pokeball.x + dist, x: pokeball.x + dist,
@ -185,3 +186,31 @@ export function sin(index: integer, amplitude: integer): number {
export function cos(index: integer, amplitude: integer): number { export function cos(index: integer, amplitude: integer): number {
return amplitude * Math.cos(index * (Math.PI / 128)); return amplitude * Math.cos(index * (Math.PI / 128));
} }
/**
* Play the shiny sparkle animation and sound effect for the given sprite
* First ensures that the animation has been properly initialized
* @param sparkleSprite the Sprite to play the animation on
* @param variant which shiny {@linkcode variant} to play the animation for
*/
export function doShinySparkleAnim(scene: BattleScene, sparkleSprite: Phaser.GameObjects.Sprite, variant: Variant) {
const keySuffix = variant ? `_${variant + 1}` : "";
const spriteKey = `shiny${keySuffix}`;
const animationKey = `sparkle${keySuffix}`;
// Make sure the animation exists, and create it if not
if (!scene.anims.exists(animationKey)) {
const frameNames = scene.anims.generateFrameNames(spriteKey, { suffix: ".png", end: 34 });
scene.anims.create({
key: `sparkle${keySuffix}`,
frames: frameNames,
frameRate: 32,
showOnStart: true,
hideOnComplete: true,
});
}
// Play the animation
sparkleSprite.play(animationKey);
scene.playSound("se/sparkle");
}

View File

@ -707,7 +707,7 @@ export class Arena {
case Biome.METROPOLIS: case Biome.METROPOLIS:
return 141.470; return 141.470;
case Biome.FOREST: case Biome.FOREST:
return 4.294; return 0.341;
case Biome.SEA: case Biome.SEA:
return 0.024; return 0.024;
case Biome.SWAMP: case Biome.SWAMP:

View File

@ -1,10 +1,12 @@
import { GameObjects } from "phaser"; import { GameObjects } from "phaser";
import BattleScene from "../battle-scene"; import BattleScene from "#app/battle-scene";
import MysteryEncounter from "../data/mystery-encounters/mystery-encounter"; import MysteryEncounter from "#app/data/mystery-encounters/mystery-encounter";
import { Species } from "#enums/species"; import { Species } from "#enums/species";
import { isNullOrUndefined } from "#app/utils"; import { isNullOrUndefined } from "#app/utils";
import { getSpriteKeysFromSpecies } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils"; import { getSpriteKeysFromSpecies } from "#app/data/mystery-encounters/utils/encounter-pokemon-utils";
import PlayAnimationConfig = Phaser.Types.Animations.PlayAnimationConfig; import PlayAnimationConfig = Phaser.Types.Animations.PlayAnimationConfig;
import { Variant } from "#app/data/variant";
import { doShinySparkleAnim } from "#app/field/anims";
type KnownFileRoot = type KnownFileRoot =
| "arenas" | "arenas"
@ -59,6 +61,10 @@ export class MysteryEncounterSpriteConfig {
scale?: number; scale?: number;
/** If you are using a Pokemon sprite, set to `true`. This will ensure variant, form, gender, shiny sprites are loaded properly */ /** If you are using a Pokemon sprite, set to `true`. This will ensure variant, form, gender, shiny sprites are loaded properly */
isPokemon?: boolean; isPokemon?: boolean;
/** If using a Pokemon shiny sprite, needs to be set to ensure the correct variant assets get loaded and displayed */
isShiny?: boolean;
/** If using a Pokemon shiny sprite, needs to be set to ensure the correct variant assets get loaded and displayed */
variant?: Variant;
/** If you are using an item sprite, set to `true` */ /** If you are using an item sprite, set to `true` */
isItem?: boolean; isItem?: boolean;
/** The sprites alpha. `0` - `1` The lower the number, the more transparent */ /** The sprites alpha. `0` - `1` The lower the number, the more transparent */
@ -74,6 +80,7 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
public encounter: MysteryEncounter; public encounter: MysteryEncounter;
public spriteConfigs: MysteryEncounterSpriteConfig[]; public spriteConfigs: MysteryEncounterSpriteConfig[];
public enterFromRight: boolean; public enterFromRight: boolean;
private shinySparkleSprites: { sprite: Phaser.GameObjects.Sprite, variant: Variant }[];
constructor(scene: BattleScene, encounter: MysteryEncounter) { constructor(scene: BattleScene, encounter: MysteryEncounter) {
super(scene, -72, 76); super(scene, -72, 76);
@ -86,7 +93,7 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
}; };
if (!isNullOrUndefined(result.species)) { if (!isNullOrUndefined(result.species)) {
const keys = getSpriteKeysFromSpecies(result.species); const keys = getSpriteKeysFromSpecies(result.species, undefined, undefined, result.isShiny, result.variant);
result.spriteKey = keys.spriteKey; result.spriteKey = keys.spriteKey;
result.fileRoot = keys.fileRoot; result.fileRoot = keys.fileRoot;
result.isPokemon = true; result.isPokemon = true;
@ -120,18 +127,36 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
// Sprites with custom X or Y defined will not count for normal spacing requirements // Sprites with custom X or Y defined will not count for normal spacing requirements
const spacingValue = Math.round((maxX - minX) / Math.max(this.spriteConfigs.filter(s => !s.x && !s.y).length, 1)); const spacingValue = Math.round((maxX - minX) / Math.max(this.spriteConfigs.filter(s => !s.x && !s.y).length, 1));
this.shinySparkleSprites = [];
const shinySparkleSprites = scene.add.container(0, 0);
this.spriteConfigs?.forEach((config) => { this.spriteConfigs?.forEach((config) => {
const { spriteKey, isItem, hasShadow, scale, x, y, yShadow, alpha } = config; const { spriteKey, isItem, hasShadow, scale, x, y, yShadow, alpha, isPokemon, isShiny, variant } = config;
let sprite: GameObjects.Sprite; let sprite: GameObjects.Sprite;
let tintSprite: GameObjects.Sprite; let tintSprite: GameObjects.Sprite;
let pokemonShinySparkle: Phaser.GameObjects.Sprite | undefined;
if (!isItem) { if (isItem) {
sprite = getSprite(spriteKey, hasShadow, yShadow);
tintSprite = getSprite(spriteKey);
} else {
sprite = getItemSprite(spriteKey, hasShadow, yShadow); sprite = getItemSprite(spriteKey, hasShadow, yShadow);
tintSprite = getItemSprite(spriteKey); tintSprite = getItemSprite(spriteKey);
} else {
sprite = getSprite(spriteKey, hasShadow, yShadow);
tintSprite = getSprite(spriteKey);
if (isPokemon && isShiny) {
// Set Pipeline for shiny variant
sprite.setPipelineData("spriteKey", spriteKey);
tintSprite.setPipelineData("spriteKey", spriteKey);
sprite.setPipelineData("shiny", true);
sprite.setPipelineData("variant", variant);
tintSprite.setPipelineData("shiny", true);
tintSprite.setPipelineData("variant", variant);
// Create Sprite for shiny Sparkle
pokemonShinySparkle = scene.add.sprite(sprite.x, sprite.y, "shiny");
pokemonShinySparkle.setOrigin(0.5, 1);
pokemonShinySparkle.setVisible(false);
this.shinySparkleSprites.push({ sprite: pokemonShinySparkle, variant: variant ?? 0 });
shinySparkleSprites.add(pokemonShinySparkle);
}
} }
sprite.setVisible(!config.hidden); sprite.setVisible(!config.hidden);
@ -165,6 +190,11 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
} }
} }
if (!isNullOrUndefined(pokemonShinySparkle)) {
// Offset the sparkle to match the Pokemon's position
pokemonShinySparkle.setPosition(sprite.x, sprite.y);
}
if (!isNullOrUndefined(alpha)) { if (!isNullOrUndefined(alpha)) {
sprite.setAlpha(alpha); sprite.setAlpha(alpha);
tintSprite.setAlpha(alpha); tintSprite.setAlpha(alpha);
@ -173,6 +203,7 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
this.add(sprite); this.add(sprite);
this.add(tintSprite); this.add(tintSprite);
}); });
this.add(shinySparkleSprites);
} }
/** /**
@ -187,6 +218,9 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
this.spriteConfigs.forEach((config) => { this.spriteConfigs.forEach((config) => {
if (config.isPokemon) { if (config.isPokemon) {
this.scene.loadPokemonAtlas(config.spriteKey, config.fileRoot); this.scene.loadPokemonAtlas(config.spriteKey, config.fileRoot);
if (config.isShiny) {
this.scene.loadPokemonVariantAssets(config.spriteKey, config.fileRoot, config.variant);
}
} else if (config.isItem) { } else if (config.isItem) {
this.scene.loadAtlas("items", ""); this.scene.loadAtlas("items", "");
} else { } else {
@ -240,11 +274,21 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
this.getSprites().map((sprite, i) => { this.getSprites().map((sprite, i) => {
if (!this.spriteConfigs[i].isItem) { if (!this.spriteConfigs[i].isItem) {
sprite.setTexture(this.spriteConfigs[i].spriteKey).setFrame(0); sprite.setTexture(this.spriteConfigs[i].spriteKey).setFrame(0);
if (sprite.texture.frameTotal > 1) {
// Show the first animation frame for a smooth transition when the animation starts.
const firstFrame = sprite.texture.frames["0001.png"];
sprite.setFrame(firstFrame ?? 0);
}
} }
}); });
this.getTintSprites().map((tintSprite, i) => { this.getTintSprites().map((tintSprite, i) => {
if (!this.spriteConfigs[i].isItem) { if (!this.spriteConfigs[i].isItem) {
tintSprite.setTexture(this.spriteConfigs[i].spriteKey).setFrame(0); tintSprite.setTexture(this.spriteConfigs[i].spriteKey).setFrame(0);
if (tintSprite.texture.frameTotal > 1) {
// Show the first frame for a smooth transition when the animation starts.
const firstFrame = tintSprite.texture.frames["0001.png"];
tintSprite.setFrame(firstFrame ?? 0);
}
} }
}); });
@ -288,6 +332,17 @@ export default class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Con
return true; return true;
} }
/**
* Play shiny sparkle animations if there are shiny Pokemon
*/
playShinySparkles() {
for (const sparkleConfig of this.shinySparkleSprites) {
this.scene.time.delayedCall(500, () => {
doShinySparkleAnim(this.scene, sparkleConfig.sprite, sparkleConfig.variant);
});
}
}
/** /**
* For sprites with animation and that do not have animation disabled, will begin frame animation * For sprites with animation and that do not have animation disabled, will begin frame animation
*/ */

View File

@ -23,13 +23,13 @@ import { reverseCompatibleTms, tmSpecies, tmPoolTiers } from "#app/data/balance/
import { BattlerTag, BattlerTagLapseType, EncoreTag, GroundedTag, HighestStatBoostTag, SubstituteTag, TypeImmuneTag, getBattlerTag, SemiInvulnerableTag, TypeBoostTag, MoveRestrictionBattlerTag, ExposedTag, DragonCheerTag, CritBoostTag, TrappedTag, TarShotTag, AutotomizedTag, PowerTrickTag } from "../data/battler-tags"; import { BattlerTag, BattlerTagLapseType, EncoreTag, GroundedTag, HighestStatBoostTag, SubstituteTag, TypeImmuneTag, getBattlerTag, SemiInvulnerableTag, TypeBoostTag, MoveRestrictionBattlerTag, ExposedTag, DragonCheerTag, CritBoostTag, TrappedTag, TarShotTag, AutotomizedTag, PowerTrickTag } from "../data/battler-tags";
import { WeatherType } from "#enums/weather-type"; import { WeatherType } from "#enums/weather-type";
import { ArenaTagSide, NoCritTag, WeakenMoveScreenTag } from "#app/data/arena-tag"; import { ArenaTagSide, NoCritTag, WeakenMoveScreenTag } from "#app/data/arena-tag";
import { Ability, AbAttr, StatMultiplierAbAttr, BlockCritAbAttr, BonusCritAbAttr, BypassBurnDamageReductionAbAttr, FieldPriorityMoveImmunityAbAttr, IgnoreOpponentStatStagesAbAttr, MoveImmunityAbAttr, PreDefendFullHpEndureAbAttr, ReceivedMoveDamageMultiplierAbAttr, StabBoostAbAttr, StatusEffectImmunityAbAttr, TypeImmunityAbAttr, WeightMultiplierAbAttr, allAbilities, applyAbAttrs, applyStatMultiplierAbAttrs, applyPreApplyBattlerTagAbAttrs, applyPreAttackAbAttrs, applyPreDefendAbAttrs, applyPreSetStatusAbAttrs, UnsuppressableAbilityAbAttr, SuppressFieldAbilitiesAbAttr, NoFusionAbilityAbAttr, MultCritAbAttr, IgnoreTypeImmunityAbAttr, DamageBoostAbAttr, IgnoreTypeStatusEffectImmunityAbAttr, ConditionalCritAbAttr, applyFieldStatMultiplierAbAttrs, FieldMultiplyStatAbAttr, AddSecondStrikeAbAttr, UserFieldStatusEffectImmunityAbAttr, UserFieldBattlerTagImmunityAbAttr, BattlerTagImmunityAbAttr, MoveTypeChangeAbAttr, FullHpResistTypeAbAttr, applyCheckTrappedAbAttrs, CheckTrappedAbAttr, PostSetStatusAbAttr, applyPostSetStatusAbAttrs, InfiltratorAbAttr, AlliedFieldDamageReductionAbAttr, PostDamageAbAttr, applyPostDamageAbAttrs, PostDamageForceSwitchAbAttr, CommanderAbAttr, applyPostItemLostAbAttrs, PostItemLostAbAttr } from "#app/data/ability"; import { Ability, AbAttr, StatMultiplierAbAttr, BlockCritAbAttr, BonusCritAbAttr, BypassBurnDamageReductionAbAttr, FieldPriorityMoveImmunityAbAttr, IgnoreOpponentStatStagesAbAttr, MoveImmunityAbAttr, PreDefendFullHpEndureAbAttr, ReceivedMoveDamageMultiplierAbAttr, StabBoostAbAttr, StatusEffectImmunityAbAttr, TypeImmunityAbAttr, WeightMultiplierAbAttr, allAbilities, applyAbAttrs, applyStatMultiplierAbAttrs, applyPreApplyBattlerTagAbAttrs, applyPreAttackAbAttrs, applyPreDefendAbAttrs, applyPreSetStatusAbAttrs, UnsuppressableAbilityAbAttr, SuppressFieldAbilitiesAbAttr, NoFusionAbilityAbAttr, MultCritAbAttr, IgnoreTypeImmunityAbAttr, DamageBoostAbAttr, IgnoreTypeStatusEffectImmunityAbAttr, ConditionalCritAbAttr, applyFieldStatMultiplierAbAttrs, FieldMultiplyStatAbAttr, AddSecondStrikeAbAttr, UserFieldStatusEffectImmunityAbAttr, UserFieldBattlerTagImmunityAbAttr, BattlerTagImmunityAbAttr, MoveTypeChangeAbAttr, FullHpResistTypeAbAttr, applyCheckTrappedAbAttrs, CheckTrappedAbAttr, PostSetStatusAbAttr, applyPostSetStatusAbAttrs, InfiltratorAbAttr, AlliedFieldDamageReductionAbAttr, PostDamageAbAttr, applyPostDamageAbAttrs, CommanderAbAttr, applyPostItemLostAbAttrs, PostItemLostAbAttr } from "#app/data/ability";
import PokemonData from "#app/system/pokemon-data"; import PokemonData from "#app/system/pokemon-data";
import { BattlerIndex } from "#app/battle"; import { BattlerIndex } from "#app/battle";
import { Mode } from "#app/ui/ui"; import { Mode } from "#app/ui/ui";
import PartyUiHandler, { PartyOption, PartyUiMode } from "#app/ui/party-ui-handler"; import PartyUiHandler, { PartyOption, PartyUiMode } from "#app/ui/party-ui-handler";
import SoundFade from "phaser3-rex-plugins/plugins/soundfade"; import SoundFade from "phaser3-rex-plugins/plugins/soundfade";
import { LevelMoves } from "#app/data/balance/pokemon-level-moves"; import { EVOLVE_MOVE, LevelMoves, RELEARN_MOVE } from "#app/data/balance/pokemon-level-moves";
import { DamageAchv, achvs } from "#app/system/achv"; import { DamageAchv, achvs } from "#app/system/achv";
import { DexAttr, StarterDataEntry, StarterMoveset } from "#app/system/game-data"; import { DexAttr, StarterDataEntry, StarterMoveset } from "#app/system/game-data";
import { QuantizerCelebi, argbFromRgba, rgbaFromArgb } from "@material/material-color-utilities"; import { QuantizerCelebi, argbFromRgba, rgbaFromArgb } from "@material/material-color-utilities";
@ -69,6 +69,16 @@ import { SpeciesFormKey } from "#enums/species-form-key";
import { BASE_HIDDEN_ABILITY_CHANCE, BASE_SHINY_CHANCE, SHINY_EPIC_CHANCE, SHINY_VARIANT_CHANCE } from "#app/data/balance/rates"; import { BASE_HIDDEN_ABILITY_CHANCE, BASE_SHINY_CHANCE, SHINY_EPIC_CHANCE, SHINY_VARIANT_CHANCE } from "#app/data/balance/rates";
import { Nature } from "#enums/nature"; import { Nature } from "#enums/nature";
import { StatusEffect } from "#enums/status-effect"; import { StatusEffect } from "#enums/status-effect";
import { doShinySparkleAnim } from "#app/field/anims";
export enum LearnMoveSituation {
MISC,
LEVEL_UP,
RELEARN,
EVOLUTION,
EVOLUTION_FUSED, // If fusionSpecies has Evolved
EVOLUTION_FUSED_BASE // If fusion's base species has Evolved
}
export enum FieldPosition { export enum FieldPosition {
CENTER, CENTER,
@ -327,6 +337,9 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
if (!this.scene) { if (!this.scene) {
return false; return false;
} }
if (this.switchOutStatus) {
return false;
}
return this.scene.field.getIndex(this) > -1; return this.scene.field.getIndex(this) > -1;
} }
@ -802,21 +815,9 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
} }
initShinySparkle(): void { initShinySparkle(): void {
const keySuffix = this.variant ? `_${this.variant + 1}` : ""; const shinySparkle = this.scene.addFieldSprite(0, 0, "shiny");
const key = `shiny${keySuffix}`;
const shinySparkle = this.scene.addFieldSprite(0, 0, key);
shinySparkle.setVisible(false); shinySparkle.setVisible(false);
shinySparkle.setOrigin(0.5, 1); shinySparkle.setOrigin(0.5, 1);
const frameNames = this.scene.anims.generateFrameNames(key, { suffix: ".png", end: 34 });
if (!(this.scene.anims.exists(`sparkle${keySuffix}`))) {
this.scene.anims.create({
key: `sparkle${keySuffix}`,
frames: frameNames,
frameRate: 32,
showOnStart: true,
hideOnComplete: true,
});
}
this.add(shinySparkle); this.add(shinySparkle);
this.shinySparkle = shinySparkle; this.shinySparkle = shinySparkle;
@ -1758,7 +1759,12 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
} }
const trappedByAbility = new Utils.BooleanHolder(false); const trappedByAbility = new Utils.BooleanHolder(false);
const opposingField = this.isPlayer() ? this.scene.getEnemyField() : this.scene.getPlayerField(); /**
* Contains opposing Pokemon (Enemy/Player Pokemon) depending on perspective
* Afterwards, it filters out Pokemon that have been switched out of the field so trapped abilities/moves do not trigger
*/
const opposingFieldUnfiltered = this.isPlayer() ? this.scene.getEnemyField() : this.scene.getPlayerField();
const opposingField = opposingFieldUnfiltered.filter(enemyPkm => enemyPkm.switchOutStatus === false);
opposingField.forEach((opponent) => opposingField.forEach((opponent) =>
applyCheckTrappedAbAttrs(CheckTrappedAbAttr, opponent, trappedByAbility, this, trappedAbMessages, simulated) applyCheckTrappedAbAttrs(CheckTrappedAbAttr, opponent, trappedByAbility, this, trappedAbMessages, simulated)
@ -1998,12 +2004,15 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
* @param {boolean} includeRelearnerMoves Whether to include moves that would require a relearner. Note the move relearner inherently allows evolution moves * @param {boolean} includeRelearnerMoves Whether to include moves that would require a relearner. Note the move relearner inherently allows evolution moves
* @returns {LevelMoves} A list of moves and the levels they can be learned at * @returns {LevelMoves} A list of moves and the levels they can be learned at
*/ */
getLevelMoves(startingLevel?: integer, includeEvolutionMoves: boolean = false, simulateEvolutionChain: boolean = false, includeRelearnerMoves: boolean = false): LevelMoves { getLevelMoves(startingLevel?: integer, includeEvolutionMoves: boolean = false, simulateEvolutionChain: boolean = false, includeRelearnerMoves: boolean = false, learnSituation: LearnMoveSituation = LearnMoveSituation.MISC): LevelMoves {
const ret: LevelMoves = []; const ret: LevelMoves = [];
let levelMoves: LevelMoves = []; let levelMoves: LevelMoves = [];
if (!startingLevel) { if (!startingLevel) {
startingLevel = this.level; startingLevel = this.level;
} }
if (learnSituation === LearnMoveSituation.EVOLUTION_FUSED && this.fusionSpecies) { // For fusion evolutions, get ONLY the moves of the component mon that evolved
levelMoves = this.getFusionSpeciesForm(true).getLevelMoves().filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || (includeRelearnerMoves && lm[0] === RELEARN_MOVE) || lm[0] > 0);
} else {
if (simulateEvolutionChain) { if (simulateEvolutionChain) {
const evolutionChain = this.species.getSimulatedEvolutionChain(this.level, this.hasTrainer(), this.isBoss(), this.isPlayer()); const evolutionChain = this.species.getSimulatedEvolutionChain(this.level, this.hasTrainer(), this.isBoss(), this.isPlayer());
for (let e = 0; e < evolutionChain.length; e++) { for (let e = 0; e < evolutionChain.length; e++) {
@ -2012,26 +2021,27 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
if (includeRelearnerMoves) { if (includeRelearnerMoves) {
levelMoves.push(...speciesLevelMoves); levelMoves.push(...speciesLevelMoves);
} else { } else {
levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === 0) || ((!e || lm[0] > 1) && (e === evolutionChain.length - 1 || lm[0] <= evolutionChain[e + 1][1])))); levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || ((!e || lm[0] > 1) && (e === evolutionChain.length - 1 || lm[0] <= evolutionChain[e + 1][1]))));
} }
} }
} else { } else {
levelMoves = this.getSpeciesForm(true).getLevelMoves().filter(lm => (includeEvolutionMoves && lm[0] === 0) || (includeRelearnerMoves && lm[0] === -1) || lm[0] > 0); levelMoves = this.getSpeciesForm(true).getLevelMoves().filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || (includeRelearnerMoves && lm[0] === RELEARN_MOVE) || lm[0] > 0);
} }
if (this.fusionSpecies) { if (this.fusionSpecies && learnSituation !== LearnMoveSituation.EVOLUTION_FUSED_BASE) { // For fusion evolutions, get ONLY the moves of the component mon that evolved
if (simulateEvolutionChain) { if (simulateEvolutionChain) {
const fusionEvolutionChain = this.fusionSpecies.getSimulatedEvolutionChain(this.level, this.hasTrainer(), this.isBoss(), this.isPlayer()); const fusionEvolutionChain = this.fusionSpecies.getSimulatedEvolutionChain(this.level, this.hasTrainer(), this.isBoss(), this.isPlayer());
for (let e = 0; e < fusionEvolutionChain.length; e++) { for (let e = 0; e < fusionEvolutionChain.length; e++) {
// TODO: Might need to pass specific form index in simulated evolution chain // TODO: Might need to pass specific form index in simulated evolution chain
const speciesLevelMoves = getPokemonSpeciesForm(fusionEvolutionChain[e][0], this.fusionFormIndex).getLevelMoves(); const speciesLevelMoves = getPokemonSpeciesForm(fusionEvolutionChain[e][0], this.fusionFormIndex).getLevelMoves();
if (includeRelearnerMoves) { if (includeRelearnerMoves) {
levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === 0) || lm[0] !== 0)); levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || lm[0] !== EVOLVE_MOVE));
} else { } else {
levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === 0) || ((!e || lm[0] > 1) && (e === fusionEvolutionChain.length - 1 || lm[0] <= fusionEvolutionChain[e + 1][1])))); levelMoves.push(...speciesLevelMoves.filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || ((!e || lm[0] > 1) && (e === fusionEvolutionChain.length - 1 || lm[0] <= fusionEvolutionChain[e + 1][1]))));
} }
} }
} else { } else {
levelMoves.push(...this.getFusionSpeciesForm(true).getLevelMoves().filter(lm => (includeEvolutionMoves && lm[0] === 0) || (includeRelearnerMoves && lm[0] === -1) || lm[0] > 0)); levelMoves.push(...this.getFusionSpeciesForm(true).getLevelMoves().filter(lm => (includeEvolutionMoves && lm[0] === EVOLVE_MOVE) || (includeRelearnerMoves && lm[0] === RELEARN_MOVE) || lm[0] > 0));
}
} }
} }
levelMoves.sort((lma: [integer, integer], lmb: [integer, integer]) => lma[0] > lmb[0] ? 1 : lma[0] < lmb[0] ? -1 : 0); levelMoves.sort((lma: [integer, integer], lmb: [integer, integer]) => lma[0] > lmb[0] ? 1 : lma[0] < lmb[0] ? -1 : 0);
@ -2146,6 +2156,7 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
/** /**
* Function that tries to set a Pokemon shiny based on seed. * Function that tries to set a Pokemon shiny based on seed.
* For manual use only, usually to roll a Pokemon's shiny chance a second time. * For manual use only, usually to roll a Pokemon's shiny chance a second time.
* If it rolls shiny, also sets a random variant and give the Pokemon the associated luck.
* *
* The base shiny odds are {@linkcode BASE_SHINY_CHANCE} / `65536` * The base shiny odds are {@linkcode BASE_SHINY_CHANCE} / `65536`
* @param thresholdOverride number that is divided by `2^16` (`65536`) to get the shiny chance, overrides {@linkcode shinyThreshold} if set (bypassing shiny rate modifiers such as Shiny Charm) * @param thresholdOverride number that is divided by `2^16` (`65536`) to get the shiny chance, overrides {@linkcode shinyThreshold} if set (bypassing shiny rate modifiers such as Shiny Charm)
@ -2171,6 +2182,8 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
this.shiny = randSeedInt(65536) < shinyThreshold.value; this.shiny = randSeedInt(65536) < shinyThreshold.value;
if (this.shiny) { if (this.shiny) {
this.variant = this.generateShinyVariant();
this.luck = this.variant + 1 + (this.fusionShiny ? this.fusionVariant + 1 : 0);
this.initShinySparkle(); this.initShinySparkle();
} }
@ -2796,8 +2809,8 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
}; };
} }
// If the attack deals fixed damaged, return a result with that much damage // If the attack deals fixed damage, return a result with that much damage
const fixedDamage = new Utils.IntegerHolder(0); const fixedDamage = new Utils.NumberHolder(0);
applyMoveAttrs(FixedDamageAttr, source, this, move, fixedDamage); applyMoveAttrs(FixedDamageAttr, source, this, move, fixedDamage);
if (fixedDamage.value) { if (fixedDamage.value) {
const multiLensMultiplier = new Utils.NumberHolder(1); const multiLensMultiplier = new Utils.NumberHolder(1);
@ -3074,14 +3087,6 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
this.turnData.damageTaken += damage; this.turnData.damageTaken += damage;
this.battleData.hitCount++; this.battleData.hitCount++;
// Multi-Lens and Parental Bond check for Wimp Out/Emergency Exit
if (this.hasAbilityWithAttr(PostDamageForceSwitchAbAttr)) {
const multiHitModifier = source.getHeldItems().find(m => m instanceof PokemonMultiHitModifier);
if (multiHitModifier || source.hasAbilityWithAttr(AddSecondStrikeAbAttr)) {
applyPostDamageAbAttrs(PostDamageAbAttr, this, damage, this.hasPassive(), false, [], source);
}
}
const attackResult = { move: move.id, result: result as DamageResult, damage: damage, critical: isCritical, sourceId: source.id, sourceBattlerIndex: source.getBattlerIndex() }; const attackResult = { move: move.id, result: result as DamageResult, damage: damage, critical: isCritical, sourceId: source.id, sourceBattlerIndex: source.getBattlerIndex() };
this.turnData.attacksReceived.unshift(attackResult); this.turnData.attacksReceived.unshift(attackResult);
if (source.isPlayer() && !this.isPlayer()) { if (source.isPlayer() && !this.isPlayer()) {
@ -3182,13 +3187,22 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
* @param ignoreFaintPhase boolean to ignore adding a FaintPhase, passsed to damage() * @param ignoreFaintPhase boolean to ignore adding a FaintPhase, passsed to damage()
* @returns integer of damage done * @returns integer of damage done
*/ */
damageAndUpdate(damage: integer, result?: DamageResult, critical: boolean = false, ignoreSegments: boolean = false, preventEndure: boolean = false, ignoreFaintPhase: boolean = false, source?: Pokemon): integer { damageAndUpdate(damage: number, result?: DamageResult, critical: boolean = false, ignoreSegments: boolean = false, preventEndure: boolean = false, ignoreFaintPhase: boolean = false, source?: Pokemon): number {
const damagePhase = new DamageAnimPhase(this.scene, this.getBattlerIndex(), damage, result as DamageResult, critical); const damagePhase = new DamageAnimPhase(this.scene, this.getBattlerIndex(), damage, result as DamageResult, critical);
this.scene.unshiftPhase(damagePhase); this.scene.unshiftPhase(damagePhase);
if (this.switchOutStatus && source) {
damage = 0;
}
damage = this.damage(damage, ignoreSegments, preventEndure, ignoreFaintPhase); damage = this.damage(damage, ignoreSegments, preventEndure, ignoreFaintPhase);
// Damage amount may have changed, but needed to be queued before calling damage function // Damage amount may have changed, but needed to be queued before calling damage function
damagePhase.updateAmount(damage); damagePhase.updateAmount(damage);
/**
* Run PostDamageAbAttr from any source of damage that is not from a multi-hit
* Multi-hits are handled in move-effect-phase.ts for PostDamageAbAttr
*/
if (!source || source.turnData.hitCount <= 1) {
applyPostDamageAbAttrs(PostDamageAbAttr, this, damage, this.hasPassive(), false, [], source); applyPostDamageAbAttrs(PostDamageAbAttr, this, damage, this.hasPassive(), false, [], source);
}
return damage; return damage;
} }
@ -3665,12 +3679,21 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
return this.gender !== Gender.GENDERLESS && pokemon.gender === (this.gender === Gender.MALE ? Gender.FEMALE : Gender.MALE); return this.gender !== Gender.GENDERLESS && pokemon.gender === (this.gender === Gender.MALE ? Gender.FEMALE : Gender.MALE);
} }
canSetStatus(effect: StatusEffect | undefined, quiet: boolean = false, overrideStatus: boolean = false, sourcePokemon: Pokemon | null = null): boolean { /**
* Checks if a status effect can be applied to the Pokemon.
*
* @param effect The {@linkcode StatusEffect} whose applicability is being checked
* @param quiet Whether in-battle messages should trigger or not
* @param overrideStatus Whether the Pokemon's current status can be overriden
* @param sourcePokemon The Pokemon that is setting the status effect
* @param ignoreField Whether any field effects (weather, terrain, etc.) should be considered
*/
canSetStatus(effect: StatusEffect | undefined, quiet: boolean = false, overrideStatus: boolean = false, sourcePokemon: Pokemon | null = null, ignoreField: boolean = false): boolean {
if (effect !== StatusEffect.FAINT) { if (effect !== StatusEffect.FAINT) {
if (overrideStatus ? this.status?.effect === effect : this.status) { if (overrideStatus ? this.status?.effect === effect : this.status) {
return false; return false;
} }
if (this.isGrounded() && this.scene.arena.terrain?.terrainType === TerrainType.MISTY) { if (this.isGrounded() && (!ignoreField && this.scene.arena.terrain?.terrainType === TerrainType.MISTY)) {
return false; return false;
} }
} }
@ -3720,7 +3743,7 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
} }
break; break;
case StatusEffect.FREEZE: case StatusEffect.FREEZE:
if (this.isOfType(Type.ICE) || (this.scene?.arena?.weather?.weatherType && [ WeatherType.SUNNY, WeatherType.HARSH_SUN ].includes(this.scene.arena.weather.weatherType))) { if (this.isOfType(Type.ICE) || (!ignoreField && (this.scene?.arena?.weather?.weatherType && [ WeatherType.SUNNY, WeatherType.HARSH_SUN ].includes(this.scene.arena.weather.weatherType)))) {
return false; return false;
} }
break; break;
@ -3908,8 +3931,16 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
setFrameRate(frameRate: integer) { setFrameRate(frameRate: integer) {
this.scene.anims.get(this.getBattleSpriteKey()).frameRate = frameRate; this.scene.anims.get(this.getBattleSpriteKey()).frameRate = frameRate;
try {
this.getSprite().play(this.getBattleSpriteKey()); this.getSprite().play(this.getBattleSpriteKey());
} catch (err: unknown) {
console.error(`Failed to play animation for ${this.getBattleSpriteKey()}`, err);
}
try {
this.getTintSprite()?.play(this.getBattleSpriteKey()); this.getTintSprite()?.play(this.getBattleSpriteKey());
} catch (err: unknown) {
console.error(`Failed to play animation for ${this.getBattleSpriteKey()}`, err);
}
} }
tint(color: number, alpha?: number, duration?: integer, ease?: string) { tint(color: number, alpha?: number, duration?: integer, ease?: string) {
@ -3974,8 +4005,7 @@ export default abstract class Pokemon extends Phaser.GameObjects.Container {
sparkle(): void { sparkle(): void {
if (this.shinySparkle) { if (this.shinySparkle) {
this.shinySparkle.play(`sparkle${this.variant ? `_${this.variant + 1}` : ""}`); doShinySparkleAnim(this.scene, this.shinySparkle, this.variant);
this.scene.playSound("se/sparkle");
} }
} }
@ -4452,28 +4482,29 @@ export class PlayerPokemon extends Pokemon {
}); });
} }
addFriendship(friendship: integer): void { addFriendship(friendship: number): void {
if (friendship > 0) {
const starterSpeciesId = this.species.getRootSpeciesId(); const starterSpeciesId = this.species.getRootSpeciesId();
const fusionStarterSpeciesId = this.isFusion() && this.fusionSpecies ? this.fusionSpecies.getRootSpeciesId() : 0; const fusionStarterSpeciesId = this.isFusion() && this.fusionSpecies ? this.fusionSpecies.getRootSpeciesId() : 0;
const starterData = [ const starterData = [
this.scene.gameData.starterData[starterSpeciesId], this.scene.gameData.starterData[starterSpeciesId],
fusionStarterSpeciesId ? this.scene.gameData.starterData[fusionStarterSpeciesId] : null fusionStarterSpeciesId ? this.scene.gameData.starterData[fusionStarterSpeciesId] : null
].filter(d => !!d); ].filter(d => !!d);
const amount = new Utils.IntegerHolder(friendship); const amount = new Utils.NumberHolder(friendship);
this.scene.applyModifier(PokemonFriendshipBoosterModifier, true, this, amount);
let candyFriendshipMultiplier = CLASSIC_CANDY_FRIENDSHIP_MULTIPLIER; let candyFriendshipMultiplier = CLASSIC_CANDY_FRIENDSHIP_MULTIPLIER;
if (this.scene.eventManager.isEventActive()) { if (this.scene.eventManager.isEventActive()) {
candyFriendshipMultiplier *= this.scene.eventManager.getFriendshipMultiplier(); candyFriendshipMultiplier *= this.scene.eventManager.getFriendshipMultiplier();
} }
const starterAmount = new Utils.IntegerHolder(Math.floor(friendship * (this.scene.gameMode.isClassic && friendship > 0 ? candyFriendshipMultiplier : 1) / (fusionStarterSpeciesId ? 2 : 1))); const starterAmount = new Utils.NumberHolder(Math.floor(amount.value * (this.scene.gameMode.isClassic ? candyFriendshipMultiplier : 1) / (fusionStarterSpeciesId ? 2 : 1)));
if (amount.value > 0) {
this.scene.applyModifier(PokemonFriendshipBoosterModifier, true, this, amount);
this.scene.applyModifier(PokemonFriendshipBoosterModifier, true, this, starterAmount);
// Add friendship to this PlayerPokemon
this.friendship = Math.min(this.friendship + amount.value, 255); this.friendship = Math.min(this.friendship + amount.value, 255);
if (this.friendship === 255) { if (this.friendship === 255) {
this.scene.validateAchv(achvs.MAX_FRIENDSHIP); this.scene.validateAchv(achvs.MAX_FRIENDSHIP);
} }
starterData.forEach((sd: StarterDataEntry, i: integer) => { // Add to candy progress for this mon's starter species and its fused species (if it has one)
starterData.forEach((sd: StarterDataEntry, i: number) => {
const speciesId = !i ? starterSpeciesId : fusionStarterSpeciesId as Species; const speciesId = !i ? starterSpeciesId : fusionStarterSpeciesId as Species;
sd.friendship = (sd.friendship || 0) + starterAmount.value; sd.friendship = (sd.friendship || 0) + starterAmount.value;
if (sd.friendship >= getStarterValueFriendshipCap(speciesStarterCosts[speciesId])) { if (sd.friendship >= getStarterValueFriendshipCap(speciesStarterCosts[speciesId])) {
@ -4482,10 +4513,8 @@ export class PlayerPokemon extends Pokemon {
} }
}); });
} else { } else {
this.friendship = Math.max(this.friendship + amount.value, 0); // Lose friendship upon fainting
for (const sd of starterData) { this.friendship = Math.max(this.friendship + friendship, 0);
sd.friendship = Math.max((sd.friendship || 0) + starterAmount.value, 0);
}
} }
} }
/** /**
@ -4818,12 +4847,13 @@ export class EnemyPokemon extends Pokemon {
public aiType: AiType; public aiType: AiType;
public bossSegments: integer; public bossSegments: integer;
public bossSegmentIndex: integer; public bossSegmentIndex: integer;
/** To indicate of the instance was populated with a dataSource -> e.g. loaded & populated from session data */ /** To indicate if the instance was populated with a dataSource -> e.g. loaded & populated from session data */
public readonly isPopulatedFromDataSource: boolean; public readonly isPopulatedFromDataSource: boolean;
constructor(scene: BattleScene, species: PokemonSpecies, level: integer, trainerSlot: TrainerSlot, boss: boolean, dataSource?: PokemonData) { constructor(scene: BattleScene, species: PokemonSpecies, level: integer, trainerSlot: TrainerSlot, boss: boolean, shinyLock: boolean = false, dataSource?: PokemonData) {
super(scene, 236, 84, species, level, dataSource?.abilityIndex, dataSource?.formIndex, super(scene, 236, 84, species, level, dataSource?.abilityIndex, dataSource?.formIndex, dataSource?.gender,
dataSource?.gender, dataSource ? dataSource.shiny : false, dataSource ? dataSource.variant : undefined, undefined, dataSource ? dataSource.nature : undefined, dataSource); (!shinyLock && dataSource) ? dataSource.shiny : false, (!shinyLock && dataSource) ? dataSource.variant : undefined,
undefined, dataSource ? dataSource.nature : undefined, dataSource);
this.trainerSlot = trainerSlot; this.trainerSlot = trainerSlot;
this.isPopulatedFromDataSource = !!dataSource; // if a dataSource is provided, then it was populated from dataSource this.isPopulatedFromDataSource = !!dataSource; // if a dataSource is provided, then it was populated from dataSource
@ -4852,12 +4882,15 @@ export class EnemyPokemon extends Pokemon {
if (!dataSource) { if (!dataSource) {
this.generateAndPopulateMoveset(); this.generateAndPopulateMoveset();
if (shinyLock || Overrides.OPP_SHINY_OVERRIDE === false) {
this.shiny = false;
} else {
this.trySetShiny(); this.trySetShiny();
if (Overrides.OPP_SHINY_OVERRIDE) { }
if (!this.shiny && Overrides.OPP_SHINY_OVERRIDE) {
this.shiny = true; this.shiny = true;
this.initShinySparkle(); this.initShinySparkle();
} else if (Overrides.OPP_SHINY_OVERRIDE === false) {
this.shiny = false;
} }
if (this.shiny) { if (this.shiny) {
@ -5528,6 +5561,7 @@ export class PokemonBattleSummonData {
export class PokemonTurnData { export class PokemonTurnData {
public flinched: boolean = false; public flinched: boolean = false;
public acted: boolean = false; public acted: boolean = false;
/** How many times the move should hit the target(s) */
public hitCount: number = 0; public hitCount: number = 0;
/** /**
* - `-1` = Calculate how many hits are left * - `-1` = Calculate how many hits are left
@ -5546,6 +5580,11 @@ export class PokemonTurnData {
public switchedInThisTurn: boolean = false; public switchedInThisTurn: boolean = false;
public failedRunAway: boolean = false; public failedRunAway: boolean = false;
public joinedRound: boolean = false; public joinedRound: boolean = false;
/**
* Used to make sure multi-hits occur properly when the user is
* forced to act again in the same turn
*/
public extraTurns: number = 0;
} }
export enum AiType { export enum AiType {

View File

@ -246,9 +246,9 @@ export class LoadingScene extends SceneBase {
} }
const availableLangs = [ "en", "de", "it", "fr", "ja", "ko", "es-ES", "pt-BR", "zh-CN" ]; const availableLangs = [ "en", "de", "it", "fr", "ja", "ko", "es-ES", "pt-BR", "zh-CN" ];
if (lang && availableLangs.includes(lang)) { if (lang && availableLangs.includes(lang)) {
this.loadImage("halloween2024-event-" + lang, "events"); this.loadImage("winter_holidays2024-event-" + lang, "events");
} else { } else {
this.loadImage("halloween2024-event-en", "events"); this.loadImage("winter_holidays2024-event-en", "events");
} }
this.loadAtlas("statuses", ""); this.loadAtlas("statuses", "");

View File

@ -1093,7 +1093,10 @@ class TmModifierTypeGenerator extends ModifierTypeGenerator {
if (pregenArgs && (pregenArgs.length === 1) && (pregenArgs[0] in Moves)) { if (pregenArgs && (pregenArgs.length === 1) && (pregenArgs[0] in Moves)) {
return new TmModifierType(pregenArgs[0] as Moves); return new TmModifierType(pregenArgs[0] as Moves);
} }
const partyMemberCompatibleTms = party.map(p => (p as PlayerPokemon).compatibleTms.filter(tm => !p.moveset.find(m => m?.moveId === tm))); const partyMemberCompatibleTms = party.map(p => {
const previousLevelMoves = p.getLearnableLevelMoves();
return (p as PlayerPokemon).compatibleTms.filter(tm => !p.moveset.find(m => m?.moveId === tm) && !previousLevelMoves.find(lm=>lm === tm));
});
const tierUniqueCompatibleTms = partyMemberCompatibleTms.flat().filter(tm => tmPoolTiers[tm] === tier).filter(tm => !allMoves[tm].name.endsWith(" (N)")).filter((tm, i, array) => array.indexOf(tm) === i); const tierUniqueCompatibleTms = partyMemberCompatibleTms.flat().filter(tm => tmPoolTiers[tm] === tier).filter(tm => !allMoves[tm].name.endsWith(" (N)")).filter((tm, i, array) => array.indexOf(tm) === i);
if (!tierUniqueCompatibleTms.length) { if (!tierUniqueCompatibleTms.length) {
return null; return null;
@ -1702,7 +1705,8 @@ const modifierPool: ModifierPool = {
new WeightedModifierType(modifierTypes.EVOLUTION_ITEM, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.EVOLUTION_ITEM, (party: Pokemon[]) => {
return Math.min(Math.ceil(party[0].scene.currentBattle.waveIndex / 15), 8); return Math.min(Math.ceil(party[0].scene.currentBattle.waveIndex / 15), 8);
}, 8), }, 8),
new WeightedModifierType(modifierTypes.MAP, (party: Pokemon[]) => party[0].scene.gameMode.isClassic && party[0].scene.currentBattle.waveIndex < 180 ? 1 : 0, 1), new WeightedModifierType(modifierTypes.MAP, (party: Pokemon[]) => party[0].scene.gameMode.isClassic && party[0].scene.currentBattle.waveIndex < 180 ? 2 : 0, 2),
new WeightedModifierType(modifierTypes.SOOTHE_BELL, 2),
new WeightedModifierType(modifierTypes.TM_GREAT, 3), new WeightedModifierType(modifierTypes.TM_GREAT, 3),
new WeightedModifierType(modifierTypes.MEMORY_MUSHROOM, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.MEMORY_MUSHROOM, (party: Pokemon[]) => {
if (!party.find(p => p.getLearnableLevelMoves().length)) { if (!party.find(p => p.getLearnableLevelMoves().length)) {
@ -1730,8 +1734,14 @@ const modifierPool: ModifierPool = {
new WeightedModifierType(modifierTypes.EVIOLITE, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.EVIOLITE, (party: Pokemon[]) => {
const { gameMode, gameData } = party[0].scene; const { gameMode, gameData } = party[0].scene;
if (gameMode.isDaily || (!gameMode.isFreshStartChallenge() && gameData.isUnlocked(Unlockables.EVIOLITE))) { if (gameMode.isDaily || (!gameMode.isFreshStartChallenge() && gameData.isUnlocked(Unlockables.EVIOLITE))) {
return party.some(p => ((p.getSpeciesForm(true).speciesId in pokemonEvolutions) || (p.isFusion() && (p.getFusionSpeciesForm(true).speciesId in pokemonEvolutions))) return party.some(p => {
&& !p.getHeldItems().some(i => i instanceof EvolutionStatBoosterModifier) && !p.isMax()) ? 10 : 0; // Check if Pokemon's species (or fusion species, if applicable) can evolve or if they're G-Max'd
if (!p.isMax() && ((p.getSpeciesForm(true).speciesId in pokemonEvolutions) || (p.isFusion() && (p.getFusionSpeciesForm(true).speciesId in pokemonEvolutions)))) {
// Check if Pokemon is already holding an Eviolite
return !p.getHeldItems().some(i => i.type.id === "EVIOLITE");
}
return false;
}) ? 10 : 0;
} }
return 0; return 0;
}), }),
@ -1744,19 +1754,59 @@ const modifierPool: ModifierPool = {
|| (p.isFusion() && checkedSpecies.includes(p.getFusionSpeciesForm(true).speciesId)))) ? 12 : 0; || (p.isFusion() && checkedSpecies.includes(p.getFusionSpeciesForm(true).speciesId)))) ? 12 : 0;
}, 12), }, 12),
new WeightedModifierType(modifierTypes.TOXIC_ORB, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.TOXIC_ORB, (party: Pokemon[]) => {
const checkedAbilities = [ Abilities.QUICK_FEET, Abilities.GUTS, Abilities.MARVEL_SCALE, Abilities.TOXIC_BOOST, Abilities.POISON_HEAL, Abilities.MAGIC_GUARD ]; return party.some(p => {
const checkedMoves = [ Moves.FACADE, Moves.TRICK, Moves.FLING, Moves.SWITCHEROO, Moves.PSYCHO_SHIFT ]; const moveset = p.getMoveset(true).filter(m => !isNullOrUndefined(m)).map(m => m.moveId);
// If a party member doesn't already have one of these two orbs and has one of the above moves or abilities, the orb can appear
return party.some(p => !p.getHeldItems().some(i => i instanceof TurnStatusEffectModifier) const canSetStatus = p.canSetStatus(StatusEffect.TOXIC, true, true, null, true);
&& (checkedAbilities.some(a => p.hasAbility(a, false, true)) const isHoldingOrb = p.getHeldItems().some(i => i.type.id === "FLAME_ORB" || i.type.id === "TOXIC_ORB");
|| p.getMoveset(true).some(m => m && checkedMoves.includes(m.moveId)))) ? 10 : 0;
// Moves that take advantage of obtaining the actual status effect
const hasStatusMoves = [ Moves.FACADE, Moves.PSYCHO_SHIFT ]
.some(m => moveset.includes(m));
// Moves that take advantage of being able to give the target a status orb
// TODO: Take moves from comment they are implemented
const hasItemMoves = [ /* Moves.TRICK, Moves.FLING, Moves.SWITCHEROO */ ]
.some(m => moveset.includes(m));
// Abilities that take advantage of obtaining the actual status effect
const hasRelevantAbilities = [ Abilities.QUICK_FEET, Abilities.GUTS, Abilities.MARVEL_SCALE, Abilities.TOXIC_BOOST, Abilities.POISON_HEAL, Abilities.MAGIC_GUARD ]
.some(a => p.hasAbility(a, false, true));
if (!isHoldingOrb) {
if (canSetStatus) {
return hasRelevantAbilities || hasStatusMoves;
} else {
return hasItemMoves;
}
}
return false;
}) ? 10 : 0;
}, 10), }, 10),
new WeightedModifierType(modifierTypes.FLAME_ORB, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.FLAME_ORB, (party: Pokemon[]) => {
const checkedAbilities = [ Abilities.QUICK_FEET, Abilities.GUTS, Abilities.MARVEL_SCALE, Abilities.FLARE_BOOST, Abilities.MAGIC_GUARD ]; return party.some(p => {
const checkedMoves = [ Moves.FACADE, Moves.TRICK, Moves.FLING, Moves.SWITCHEROO, Moves.PSYCHO_SHIFT ]; const moveset = p.getMoveset(true).filter(m => !isNullOrUndefined(m)).map(m => m.moveId);
// If a party member doesn't already have one of these two orbs and has one of the above moves or abilities, the orb can appear const canSetStatus = p.canSetStatus(StatusEffect.BURN, true, true, null, true);
return party.some(p => !p.getHeldItems().some(i => i instanceof TurnStatusEffectModifier) const isHoldingOrb = p.getHeldItems().some(i => i.type.id === "FLAME_ORB" || i.type.id === "TOXIC_ORB");
&& (checkedAbilities.some(a => p.hasAbility(a, false, true)) || p.getMoveset(true).some(m => m && checkedMoves.includes(m.moveId)))) ? 10 : 0;
// Moves that take advantage of obtaining the actual status effect
const hasStatusMoves = [ Moves.FACADE, Moves.PSYCHO_SHIFT ]
.some(m => moveset.includes(m));
// Moves that take advantage of being able to give the target a status orb
// TODO: Take moves from comment they are implemented
const hasItemMoves = [ /* Moves.TRICK, Moves.FLING, Moves.SWITCHEROO */ ]
.some(m => moveset.includes(m));
// Abilities that take advantage of obtaining the actual status effect
const hasRelevantAbilities = [ Abilities.QUICK_FEET, Abilities.GUTS, Abilities.MARVEL_SCALE, Abilities.FLARE_BOOST, Abilities.MAGIC_GUARD ]
.some(a => p.hasAbility(a, false, true));
if (!isHoldingOrb) {
if (canSetStatus) {
return hasRelevantAbilities || hasStatusMoves;
} else {
return hasItemMoves;
}
}
return false;
}) ? 10 : 0;
}, 10), }, 10),
new WeightedModifierType(modifierTypes.WHITE_HERB, (party: Pokemon[]) => { new WeightedModifierType(modifierTypes.WHITE_HERB, (party: Pokemon[]) => {
const checkedAbilities = [ Abilities.WEAK_ARMOR, Abilities.CONTRARY, Abilities.MOODY, Abilities.ANGER_SHELL, Abilities.COMPETITIVE, Abilities.DEFIANT ]; const checkedAbilities = [ Abilities.WEAK_ARMOR, Abilities.CONTRARY, Abilities.MOODY, Abilities.ANGER_SHELL, Abilities.COMPETITIVE, Abilities.DEFIANT ];
@ -1794,7 +1844,6 @@ const modifierPool: ModifierPool = {
new WeightedModifierType(modifierTypes.SOUL_DEW, 7), new WeightedModifierType(modifierTypes.SOUL_DEW, 7),
//new WeightedModifierType(modifierTypes.OVAL_CHARM, 6), //new WeightedModifierType(modifierTypes.OVAL_CHARM, 6),
new WeightedModifierType(modifierTypes.CATCHING_CHARM, (party: Pokemon[]) => !party[0].scene.gameMode.isFreshStartChallenge() && party[0].scene.gameData.getSpeciesCount(d => !!d.caughtAttr) > 100 ? 4 : 0, 4), new WeightedModifierType(modifierTypes.CATCHING_CHARM, (party: Pokemon[]) => !party[0].scene.gameMode.isFreshStartChallenge() && party[0].scene.gameData.getSpeciesCount(d => !!d.caughtAttr) > 100 ? 4 : 0, 4),
new WeightedModifierType(modifierTypes.SOOTHE_BELL, 4),
new WeightedModifierType(modifierTypes.ABILITY_CHARM, skipInClassicAfterWave(189, 6)), new WeightedModifierType(modifierTypes.ABILITY_CHARM, skipInClassicAfterWave(189, 6)),
new WeightedModifierType(modifierTypes.FOCUS_BAND, 5), new WeightedModifierType(modifierTypes.FOCUS_BAND, 5),
new WeightedModifierType(modifierTypes.KINGS_ROCK, 3), new WeightedModifierType(modifierTypes.KINGS_ROCK, 3),

View File

@ -18,7 +18,6 @@ import type { VoucherType } from "#app/system/voucher";
import { Command } from "#app/ui/command-ui-handler"; import { Command } from "#app/ui/command-ui-handler";
import { addTextObject, TextStyle } from "#app/ui/text"; import { addTextObject, TextStyle } from "#app/ui/text";
import { BooleanHolder, hslToHex, isNullOrUndefined, NumberHolder, toDmgValue } from "#app/utils"; import { BooleanHolder, hslToHex, isNullOrUndefined, NumberHolder, toDmgValue } from "#app/utils";
import { Abilities } from "#enums/abilities";
import { BattlerTagType } from "#enums/battler-tag-type"; import { BattlerTagType } from "#enums/battler-tag-type";
import { BerryType } from "#enums/berry-type"; import { BerryType } from "#enums/berry-type";
import { Moves } from "#enums/moves"; import { Moves } from "#enums/moves";
@ -726,22 +725,6 @@ export abstract class PokemonHeldItemModifier extends PersistentModifier {
return 1; return 1;
} }
//Applies to items with chance of activating secondary effects ie Kings Rock
getSecondaryChanceMultiplier(pokemon: Pokemon): number {
// Temporary quickfix to stop game from freezing when the opponet uses u-turn while holding on to king's rock
if (!pokemon.getLastXMoves()[0]) {
return 1;
}
const sheerForceAffected = allMoves[pokemon.getLastXMoves()[0].move].chance >= 0 && pokemon.hasAbility(Abilities.SHEER_FORCE);
if (sheerForceAffected) {
return 0;
} else if (pokemon.hasAbility(Abilities.SERENE_GRACE)) {
return 2;
}
return 1;
}
getMaxStackCount(scene: BattleScene, forThreshold?: boolean): number { getMaxStackCount(scene: BattleScene, forThreshold?: boolean): number {
const pokemon = this.getPokemon(scene); const pokemon = this.getPokemon(scene);
if (!pokemon) { if (!pokemon) {
@ -1614,9 +1597,16 @@ export class BypassSpeedChanceModifier extends PokemonHeldItemModifier {
} }
} }
/**
* Class for Pokemon held items like King's Rock
* Because King's Rock can be stacked in PokeRogue, unlike mainline, it does not receive a boost from Abilities.SERENE_GRACE
*/
export class FlinchChanceModifier extends PokemonHeldItemModifier { export class FlinchChanceModifier extends PokemonHeldItemModifier {
private chance: number;
constructor(type: ModifierType, pokemonId: number, stackCount?: number) { constructor(type: ModifierType, pokemonId: number, stackCount?: number) {
super(type, pokemonId, stackCount); super(type, pokemonId, stackCount);
this.chance = 10;
} }
matchType(modifier: Modifier) { matchType(modifier: Modifier) {
@ -1644,7 +1634,8 @@ export class FlinchChanceModifier extends PokemonHeldItemModifier {
* @returns `true` if {@linkcode FlinchChanceModifier} has been applied * @returns `true` if {@linkcode FlinchChanceModifier} has been applied
*/ */
override apply(pokemon: Pokemon, flinched: BooleanHolder): boolean { override apply(pokemon: Pokemon, flinched: BooleanHolder): boolean {
if (!flinched.value && pokemon.randSeedInt(10) < (this.getStackCount() * this.getSecondaryChanceMultiplier(pokemon))) { // The check for pokemon.battleSummonData is to ensure that a crash doesn't occur when a Pokemon with King's Rock procs a flinch
if (pokemon.battleSummonData && !flinched.value && pokemon.randSeedInt(100) < (this.getStackCount() * this.chance)) {
flinched.value = true; flinched.value = true;
return true; return true;
} }
@ -1652,7 +1643,7 @@ export class FlinchChanceModifier extends PokemonHeldItemModifier {
return false; return false;
} }
getMaxHeldItemCount(pokemon: Pokemon): number { getMaxHeldItemCount(_pokemon: Pokemon): number {
return 3; return 3;
} }
} }

View File

@ -86,6 +86,8 @@ class DefaultOverrides {
readonly ITEM_UNLOCK_OVERRIDE: Unlockables[] = []; readonly ITEM_UNLOCK_OVERRIDE: Unlockables[] = [];
/** Set to `true` to show all tutorials */ /** Set to `true` to show all tutorials */
readonly BYPASS_TUTORIAL_SKIP_OVERRIDE: boolean = false; readonly BYPASS_TUTORIAL_SKIP_OVERRIDE: boolean = false;
/** Set to `true` to be able to re-earn already unlocked achievements */
readonly ACHIEVEMENTS_REUNLOCK_OVERRIDE: boolean = false;
/** Set to `true` to force Paralysis and Freeze to always activate, or `false` to force them to not activate */ /** Set to `true` to force Paralysis and Freeze to always activate, or `false` to force them to not activate */
readonly STATUS_ACTIVATION_OVERRIDE: boolean | null = null; readonly STATUS_ACTIVATION_OVERRIDE: boolean | null = null;
@ -175,7 +177,11 @@ class DefaultOverrides {
// MYSTERY ENCOUNTER OVERRIDES // MYSTERY ENCOUNTER OVERRIDES
// ------------------------- // -------------------------
/** 1 to 256, set to null to ignore */ /**
* `1` (almost never) to `256` (always), set to `null` to disable the override
*
* Note: Make sure `STARTING_WAVE_OVERRIDE > 10`, otherwise MEs won't trigger
*/
readonly MYSTERY_ENCOUNTER_RATE_OVERRIDE: number | null = null; readonly MYSTERY_ENCOUNTER_RATE_OVERRIDE: number | null = null;
readonly MYSTERY_ENCOUNTER_TIER_OVERRIDE: MysteryEncounterTier | null = null; readonly MYSTERY_ENCOUNTER_TIER_OVERRIDE: MysteryEncounterTier | null = null;
readonly MYSTERY_ENCOUNTER_OVERRIDE: MysteryEncounterType | null = null; readonly MYSTERY_ENCOUNTER_OVERRIDE: MysteryEncounterType | null = null;

View File

@ -52,7 +52,7 @@ export class AttemptRunPhase extends PokemonPhase {
enemyPokemon.trySetStatus(StatusEffect.FAINT); enemyPokemon.trySetStatus(StatusEffect.FAINT);
}); });
this.scene.pushPhase(new BattleEndPhase(this.scene)); this.scene.pushPhase(new BattleEndPhase(this.scene, false));
this.scene.pushPhase(new NewBattlePhase(this.scene)); this.scene.pushPhase(new NewBattlePhase(this.scene));
} else { } else {
playerPokemon.turnData.failedRunAway = true; playerPokemon.turnData.failedRunAway = true;

View File

@ -8,7 +8,7 @@ export class BattleEndPhase extends BattlePhase {
/** If true, will increment battles won */ /** If true, will increment battles won */
isVictory: boolean; isVictory: boolean;
constructor(scene: BattleScene, isVictory: boolean = true) { constructor(scene: BattleScene, isVictory: boolean) {
super(scene); super(scene);
this.isVictory = isVictory; this.isVictory = isVictory;
@ -17,16 +17,17 @@ export class BattleEndPhase extends BattlePhase {
start() { start() {
super.start(); super.start();
this.scene.gameData.gameStats.battles++;
if (this.scene.gameMode.isEndless && this.scene.currentBattle.waveIndex + 1 > this.scene.gameData.gameStats.highestEndlessWave) {
this.scene.gameData.gameStats.highestEndlessWave = this.scene.currentBattle.waveIndex + 1;
}
if (this.isVictory) { if (this.isVictory) {
this.scene.currentBattle.addBattleScore(this.scene); this.scene.currentBattle.addBattleScore(this.scene);
this.scene.gameData.gameStats.battles++;
if (this.scene.currentBattle.trainer) { if (this.scene.currentBattle.trainer) {
this.scene.gameData.gameStats.trainersDefeated++; this.scene.gameData.gameStats.trainersDefeated++;
} }
if (this.scene.gameMode.isEndless && this.scene.currentBattle.waveIndex + 1 > this.scene.gameData.gameStats.highestEndlessWave) {
this.scene.gameData.gameStats.highestEndlessWave = this.scene.currentBattle.waveIndex + 1;
}
} }
// Endless graceful end // Endless graceful end
@ -42,7 +43,7 @@ export class BattleEndPhase extends BattlePhase {
} }
for (const pokemon of this.scene.getPokemonAllowedInBattle()) { for (const pokemon of this.scene.getPokemonAllowedInBattle()) {
applyPostBattleAbAttrs(PostBattleAbAttr, pokemon); applyPostBattleAbAttrs(PostBattleAbAttr, pokemon, false, this.isVictory);
} }
if (this.scene.currentBattle.moneyScattered) { if (this.scene.currentBattle.moneyScattered) {

View File

@ -5,7 +5,6 @@ import { getPokemonNameWithAffix } from "#app/messages";
import { Mode } from "#app/ui/ui"; import { Mode } from "#app/ui/ui";
import i18next from "i18next"; import i18next from "i18next";
import { BattlePhase } from "./battle-phase"; import { BattlePhase } from "./battle-phase";
import { PostSummonPhase } from "./post-summon-phase";
import { SummonMissingPhase } from "./summon-missing-phase"; import { SummonMissingPhase } from "./summon-missing-phase";
import { SwitchPhase } from "./switch-phase"; import { SwitchPhase } from "./switch-phase";
import { SwitchType } from "#enums/switch-type"; import { SwitchType } from "#enums/switch-type";
@ -54,7 +53,6 @@ export class CheckSwitchPhase extends BattlePhase {
this.scene.ui.showText(i18next.t("battle:switchQuestion", { pokemonName: this.useName ? getPokemonNameWithAffix(pokemon) : i18next.t("battle:pokemon") }), null, () => { this.scene.ui.showText(i18next.t("battle:switchQuestion", { pokemonName: this.useName ? getPokemonNameWithAffix(pokemon) : i18next.t("battle:pokemon") }), null, () => {
this.scene.ui.setMode(Mode.CONFIRM, () => { this.scene.ui.setMode(Mode.CONFIRM, () => {
this.scene.ui.setMode(Mode.MESSAGE); this.scene.ui.setMode(Mode.MESSAGE);
this.scene.tryRemovePhase(p => p instanceof PostSummonPhase && p.player && p.fieldIndex === this.fieldIndex);
this.scene.unshiftPhase(new SwitchPhase(this.scene, SwitchType.INITIAL_SWITCH, this.fieldIndex, false, true)); this.scene.unshiftPhase(new SwitchPhase(this.scene, SwitchType.INITIAL_SWITCH, this.fieldIndex, false, true));
this.end(); this.end();
}, () => { }, () => {

View File

@ -14,6 +14,7 @@ import SoundFade from "phaser3-rex-plugins/plugins/soundfade";
import * as Utils from "#app/utils"; import * as Utils from "#app/utils";
import { EggLapsePhase } from "./egg-lapse-phase"; import { EggLapsePhase } from "./egg-lapse-phase";
import { EggHatchData } from "#app/data/egg-hatch-data"; import { EggHatchData } from "#app/data/egg-hatch-data";
import { doShinySparkleAnim } from "#app/field/anims";
/** /**
@ -329,7 +330,12 @@ export class EggHatchPhase extends Phase {
this.scene.validateAchv(achvs.HATCH_SHINY); this.scene.validateAchv(achvs.HATCH_SHINY);
} }
this.eggContainer.setVisible(false); this.eggContainer.setVisible(false);
this.pokemonSprite.play(this.pokemon.getSpriteKey(true)); const spriteKey = this.pokemon.getSpriteKey(true);
try {
this.pokemonSprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
this.pokemonSprite.setPipelineData("ignoreTimeTint", true); this.pokemonSprite.setPipelineData("ignoreTimeTint", true);
this.pokemonSprite.setPipelineData("spriteKey", this.pokemon.getSpriteKey()); this.pokemonSprite.setPipelineData("spriteKey", this.pokemon.getSpriteKey());
this.pokemonSprite.setPipelineData("shiny", this.pokemon.shiny); this.pokemonSprite.setPipelineData("shiny", this.pokemon.shiny);
@ -341,8 +347,7 @@ export class EggHatchPhase extends Phase {
this.pokemon.cry(); this.pokemon.cry();
if (isShiny) { if (isShiny) {
this.scene.time.delayedCall(Utils.fixedInt(500), () => { this.scene.time.delayedCall(Utils.fixedInt(500), () => {
this.pokemonShinySparkle.play(`sparkle${this.pokemon.variant ? `_${this.pokemon.variant + 1}` : ""}`); doShinySparkleAnim(this.scene, this.pokemonShinySparkle, this.pokemon.variant);
this.scene.playSound("se/sparkle");
}); });
} }
this.scene.time.delayedCall(Utils.fixedInt(!this.skipped ? !isShiny ? 1250 : 1750 : !isShiny ? 250 : 750), () => { this.scene.time.delayedCall(Utils.fixedInt(!this.skipped ? !isShiny ? 1250 : 1750 : !isShiny ? 250 : 750), () => {

View File

@ -34,7 +34,7 @@ export class EggLapsePhase extends Phase {
if (eggsToHatchCount >= this.minEggsToSkip && this.scene.eggSkipPreference === 1) { if (eggsToHatchCount >= this.minEggsToSkip && this.scene.eggSkipPreference === 1) {
this.scene.ui.showText(i18next.t("battle:eggHatching"), 0, () => { this.scene.ui.showText(i18next.t("battle:eggHatching"), 0, () => {
// show prompt for skip, blocking inputs for 1 second // show prompt for skip, blocking inputs for 1 second
this.scene.ui.showText(i18next.t("battle:eggSkipPrompt"), 0); this.scene.ui.showText(i18next.t("battle:eggSkipPrompt", { eggsToHatch: eggsToHatchCount }), 0);
this.scene.ui.setModeWithoutClear(Mode.CONFIRM, () => { this.scene.ui.setModeWithoutClear(Mode.CONFIRM, () => {
this.hatchEggsSkipped(eggsToHatch); this.hatchEggsSkipped(eggsToHatch);
this.showSummary(); this.showSummary();

View File

@ -34,6 +34,7 @@ import { Biome } from "#enums/biome";
import { MysteryEncounterMode } from "#enums/mystery-encounter-mode"; import { MysteryEncounterMode } from "#enums/mystery-encounter-mode";
import { PlayerGender } from "#enums/player-gender"; import { PlayerGender } from "#enums/player-gender";
import { Species } from "#enums/species"; import { Species } from "#enums/species";
import { overrideHeldItems, overrideModifiers } from "#app/modifier/modifier";
import i18next from "i18next"; import i18next from "i18next";
import { WEIGHT_INCREMENT_ON_SPAWN_MISS } from "#app/data/mystery-encounters/mystery-encounters"; import { WEIGHT_INCREMENT_ON_SPAWN_MISS } from "#app/data/mystery-encounters/mystery-encounters";
@ -217,6 +218,11 @@ export class EncounterPhase extends BattlePhase {
if (!this.loaded && battle.battleType !== BattleType.MYSTERY_ENCOUNTER) { if (!this.loaded && battle.battleType !== BattleType.MYSTERY_ENCOUNTER) {
regenerateModifierPoolThresholds(this.scene.getEnemyField(), battle.battleType === BattleType.TRAINER ? ModifierPoolType.TRAINER : ModifierPoolType.WILD); regenerateModifierPoolThresholds(this.scene.getEnemyField(), battle.battleType === BattleType.TRAINER ? ModifierPoolType.TRAINER : ModifierPoolType.WILD);
this.scene.generateEnemyModifiers(); this.scene.generateEnemyModifiers();
overrideModifiers(this.scene, false);
this.scene.getEnemyField().forEach(enemy => {
overrideHeldItems(this.scene, enemy, false);
});
} }
this.scene.ui.setMode(Mode.MESSAGE).then(() => { this.scene.ui.setMode(Mode.MESSAGE).then(() => {
@ -380,6 +386,9 @@ export class EncounterPhase extends BattlePhase {
if (encounter.onVisualsStart) { if (encounter.onVisualsStart) {
encounter.onVisualsStart(this.scene); encounter.onVisualsStart(this.scene);
} else if (encounter.spriteConfigs && introVisuals) {
// If the encounter doesn't have any special visual intro, show sparkle for shiny Pokemon
introVisuals.playShinySparkles();
} }
const doEncounter = () => { const doEncounter = () => {

View File

@ -1,17 +1,18 @@
import SoundFade from "phaser3-rex-plugins/plugins/soundfade"; import SoundFade from "phaser3-rex-plugins/plugins/soundfade";
import { Phase } from "#app/phase"; import { Phase } from "#app/phase";
import BattleScene, { AnySound } from "#app/battle-scene"; import BattleScene, { AnySound } from "#app/battle-scene";
import { SpeciesFormEvolution } from "#app/data/balance/pokemon-evolutions"; import { FusionSpeciesFormEvolution, SpeciesFormEvolution } from "#app/data/balance/pokemon-evolutions";
import EvolutionSceneHandler from "#app/ui/evolution-scene-handler"; import EvolutionSceneHandler from "#app/ui/evolution-scene-handler";
import * as Utils from "#app/utils"; import * as Utils from "#app/utils";
import { Mode } from "#app/ui/ui"; import { Mode } from "#app/ui/ui";
import { cos, sin } from "#app/field/anims"; import { cos, sin } from "#app/field/anims";
import Pokemon, { PlayerPokemon } from "#app/field/pokemon"; import Pokemon, { LearnMoveSituation, PlayerPokemon } from "#app/field/pokemon";
import { getTypeRgb } from "#app/data/type"; import { getTypeRgb } from "#app/data/type";
import i18next from "i18next"; import i18next from "i18next";
import { getPokemonNameWithAffix } from "#app/messages"; import { getPokemonNameWithAffix } from "#app/messages";
import { LearnMovePhase } from "#app/phases/learn-move-phase"; import { LearnMovePhase } from "#app/phases/learn-move-phase";
import { EndEvolutionPhase } from "#app/phases/end-evolution-phase"; import { EndEvolutionPhase } from "#app/phases/end-evolution-phase";
import { EVOLVE_MOVE } from "#app/data/balance/pokemon-level-moves";
export class EvolutionPhase extends Phase { export class EvolutionPhase extends Phase {
protected pokemon: PlayerPokemon; protected pokemon: PlayerPokemon;
@ -20,6 +21,7 @@ export class EvolutionPhase extends Phase {
private preEvolvedPokemonName: string; private preEvolvedPokemonName: string;
private evolution: SpeciesFormEvolution | null; private evolution: SpeciesFormEvolution | null;
private fusionSpeciesEvolved: boolean; // Whether the evolution is of the fused species
private evolutionBgm: AnySound; private evolutionBgm: AnySound;
private evolutionHandler: EvolutionSceneHandler; private evolutionHandler: EvolutionSceneHandler;
@ -39,6 +41,7 @@ export class EvolutionPhase extends Phase {
this.pokemon = pokemon; this.pokemon = pokemon;
this.evolution = evolution; this.evolution = evolution;
this.lastLevel = lastLevel; this.lastLevel = lastLevel;
this.fusionSpeciesEvolved = evolution instanceof FusionSpeciesFormEvolution;
} }
validate(): boolean { validate(): boolean {
@ -102,7 +105,13 @@ export class EvolutionPhase extends Phase {
this.scene.ui.add(this.evolutionOverlay); this.scene.ui.add(this.evolutionOverlay);
[ this.pokemonSprite, this.pokemonTintSprite, this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => { [ this.pokemonSprite, this.pokemonTintSprite, this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => {
sprite.play(this.pokemon.getSpriteKey(true)); const spriteKey = this.pokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipeline(this.scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(this.pokemon.getTeraType()) }); sprite.setPipeline(this.scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(this.pokemon.getTeraType()) });
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", this.pokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", this.pokemon.getSpriteKey());
@ -127,7 +136,13 @@ export class EvolutionPhase extends Phase {
this.pokemon.getPossibleEvolution(this.evolution).then(evolvedPokemon => { this.pokemon.getPossibleEvolution(this.evolution).then(evolvedPokemon => {
[ this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => { [ this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => {
sprite.play(evolvedPokemon.getSpriteKey(true)); const spriteKey = evolvedPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", evolvedPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", evolvedPokemon.getSpriteKey());
sprite.setPipelineData("shiny", evolvedPokemon.shiny); sprite.setPipelineData("shiny", evolvedPokemon.shiny);
@ -261,7 +276,8 @@ export class EvolutionPhase extends Phase {
this.evolutionHandler.canCancel = false; this.evolutionHandler.canCancel = false;
this.pokemon.evolve(this.evolution, this.pokemon.species).then(() => { this.pokemon.evolve(this.evolution, this.pokemon.species).then(() => {
const levelMoves = this.pokemon.getLevelMoves(this.lastLevel + 1, true); const learnSituation: LearnMoveSituation = this.fusionSpeciesEvolved ? LearnMoveSituation.EVOLUTION_FUSED : this.pokemon.fusionSpecies ? LearnMoveSituation.EVOLUTION_FUSED_BASE : LearnMoveSituation.EVOLUTION;
const levelMoves = this.pokemon.getLevelMoves(this.lastLevel + 1, true, false, false, learnSituation).filter(lm => lm[0] === EVOLVE_MOVE);
for (const lm of levelMoves) { for (const lm of levelMoves) {
this.scene.unshiftPhase(new LearnMovePhase(this.scene, this.scene.getPlayerParty().indexOf(this.pokemon), lm[1])); this.scene.unshiftPhase(new LearnMovePhase(this.scene, this.scene.getPlayerParty().indexOf(this.pokemon), lm[1]));
} }

View File

@ -39,7 +39,13 @@ export class FormChangePhase extends EvolutionPhase {
this.pokemon.getPossibleForm(this.formChange).then(transformedPokemon => { this.pokemon.getPossibleForm(this.formChange).then(transformedPokemon => {
[ this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => { [ this.pokemonEvoSprite, this.pokemonEvoTintSprite ].map(sprite => {
sprite.play(transformedPokemon.getSpriteKey(true)); const spriteKey = transformedPokemon.getSpriteKey(true);
try {
sprite.play(spriteKey);
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipelineData("ignoreTimeTint", true); sprite.setPipelineData("ignoreTimeTint", true);
sprite.setPipelineData("spriteKey", transformedPokemon.getSpriteKey()); sprite.setPipelineData("spriteKey", transformedPokemon.getSpriteKey());
sprite.setPipelineData("shiny", transformedPokemon.shiny); sprite.setPipelineData("shiny", transformedPokemon.shiny);

View File

@ -23,6 +23,12 @@ import * as Utils from "#app/utils";
import { PlayerGender } from "#enums/player-gender"; import { PlayerGender } from "#enums/player-gender";
import { TrainerType } from "#enums/trainer-type"; import { TrainerType } from "#enums/trainer-type";
import i18next from "i18next"; import i18next from "i18next";
import { SessionSaveData } from "#app/system/game-data";
import PersistentModifierData from "#app/system/modifier-data";
import PokemonData from "#app/system/pokemon-data";
import ChallengeData from "#app/system/challenge-data";
import TrainerData from "#app/system/trainer-data";
import ArenaData from "#app/system/arena-data";
import { pokerogueApi } from "#app/plugins/api/pokerogue-api"; import { pokerogueApi } from "#app/plugins/api/pokerogue-api";
export class GameOverPhase extends BattlePhase { export class GameOverPhase extends BattlePhase {
@ -109,7 +115,7 @@ export class GameOverPhase extends BattlePhase {
this.scene.gameData.gameStats.dailyRunSessionsWon++; this.scene.gameData.gameStats.dailyRunSessionsWon++;
} }
} }
this.scene.gameData.saveRunHistory(this.scene, this.scene.gameData.getSessionSaveData(this.scene), this.isVictory);
const fadeDuration = this.isVictory ? 10000 : 5000; const fadeDuration = this.isVictory ? 10000 : 5000;
this.scene.fadeOutBgm(fadeDuration, true); this.scene.fadeOutBgm(fadeDuration, true);
const activeBattlers = this.scene.getField().filter(p => p?.isActive(true)); const activeBattlers = this.scene.getField().filter(p => p?.isActive(true));
@ -135,8 +141,11 @@ export class GameOverPhase extends BattlePhase {
this.scene.unshiftPhase(new GameOverModifierRewardPhase(this.scene, modifierTypes.VOUCHER_PREMIUM)); this.scene.unshiftPhase(new GameOverModifierRewardPhase(this.scene, modifierTypes.VOUCHER_PREMIUM));
} }
} }
this.getRunHistoryEntry().then(runHistoryEntry => {
this.scene.gameData.saveRunHistory(this.scene, runHistoryEntry, this.isVictory);
this.scene.pushPhase(new PostGameOverPhase(this.scene, endCardPhase)); this.scene.pushPhase(new PostGameOverPhase(this.scene, endCardPhase));
this.end(); this.end();
});
}; };
if (this.isVictory && this.scene.gameMode.isClassic) { if (this.isVictory && this.scene.gameMode.isClassic) {
@ -212,5 +221,34 @@ export class GameOverPhase extends BattlePhase {
this.firstRibbons.push(getPokemonSpecies(pokemon.species.getRootSpeciesId(forStarter))); this.firstRibbons.push(getPokemonSpecies(pokemon.species.getRootSpeciesId(forStarter)));
} }
} }
/**
* Slightly modified version of {@linkcode GameData.getSessionSaveData}.
* @returns A promise containing the {@linkcode SessionSaveData}
*/
private async getRunHistoryEntry(): Promise<SessionSaveData> {
const preWaveSessionData = await this.scene.gameData.getSession(this.scene.sessionSlotId);
return {
seed: this.scene.seed,
playTime: this.scene.sessionPlayTime,
gameMode: this.scene.gameMode.modeId,
party: this.scene.getPlayerParty().map(p => new PokemonData(p)),
enemyParty: this.scene.getEnemyParty().map(p => new PokemonData(p)),
modifiers: preWaveSessionData ? preWaveSessionData.modifiers : this.scene.findModifiers(() => true).map(m => new PersistentModifierData(m, true)),
enemyModifiers: preWaveSessionData ? preWaveSessionData.enemyModifiers : this.scene.findModifiers(() => true, false).map(m => new PersistentModifierData(m, false)),
arena: new ArenaData(this.scene.arena),
pokeballCounts: this.scene.pokeballCounts,
money: Math.floor(this.scene.money),
score: this.scene.score,
waveIndex: this.scene.currentBattle.waveIndex,
battleType: this.scene.currentBattle.battleType,
trainer: this.scene.currentBattle.trainer ? new TrainerData(this.scene.currentBattle.trainer) : null,
gameVersion: this.scene.game.config.gameVersion,
timestamp: new Date().getTime(),
challenges: this.scene.gameMode.challenges.map(c => new ChallengeData(c)),
mysteryEncounterType: this.scene.currentBattle.mysteryEncounter?.encounterType ?? -1,
mysteryEncounterSaveData: this.scene.mysteryEncounterSaveData
} as SessionSaveData;
}
} }

View File

@ -4,11 +4,13 @@ import {
AddSecondStrikeAbAttr, AddSecondStrikeAbAttr,
AlwaysHitAbAttr, AlwaysHitAbAttr,
applyPostAttackAbAttrs, applyPostAttackAbAttrs,
applyPostDamageAbAttrs,
applyPostDefendAbAttrs, applyPostDefendAbAttrs,
applyPreAttackAbAttrs, applyPreAttackAbAttrs,
IgnoreMoveEffectsAbAttr, IgnoreMoveEffectsAbAttr,
MaxMultiHitAbAttr, MaxMultiHitAbAttr,
PostAttackAbAttr, PostAttackAbAttr,
PostDamageAbAttr,
PostDefendAbAttr, PostDefendAbAttr,
TypeImmunityAbAttr, TypeImmunityAbAttr,
} from "#app/data/ability"; } from "#app/data/ability";
@ -54,7 +56,7 @@ import {
PokemonMultiHitModifier, PokemonMultiHitModifier,
} from "#app/modifier/modifier"; } from "#app/modifier/modifier";
import { PokemonPhase } from "#app/phases/pokemon-phase"; import { PokemonPhase } from "#app/phases/pokemon-phase";
import { BooleanHolder, executeIf, NumberHolder } from "#app/utils"; import { BooleanHolder, executeIf, isNullOrUndefined, NumberHolder } from "#app/utils";
import { BattlerTagType } from "#enums/battler-tag-type"; import { BattlerTagType } from "#enums/battler-tag-type";
import { Moves } from "#enums/moves"; import { Moves } from "#enums/moves";
import i18next from "i18next"; import i18next from "i18next";
@ -104,9 +106,11 @@ export class MoveEffectPhase extends PokemonPhase {
*/ */
return super.end(); return super.end();
} }
if (isNullOrUndefined(user.turnData)) {
user.resetTurnData(); user.resetTurnData();
} }
} }
}
/** /**
* Does an effect from this move override other effects on this turn? * Does an effect from this move override other effects on this turn?
@ -125,6 +129,14 @@ export class MoveEffectPhase extends PokemonPhase {
user.lapseTags(BattlerTagLapseType.MOVE_EFFECT); user.lapseTags(BattlerTagLapseType.MOVE_EFFECT);
// If the user is acting again (such as due to Instruct), reset hitsLeft/hitCount so that
// the move executes correctly (ensures all hits of a multi-hit are properly calculated)
if (user.turnData.hitsLeft === 0 && user.turnData.hitCount > 0 && user.turnData.extraTurns > 0) {
user.turnData.hitsLeft = -1;
user.turnData.hitCount = 0;
user.turnData.extraTurns--;
}
/** /**
* If this phase is for the first hit of the invoked move, * If this phase is for the first hit of the invoked move,
* resolve the move's total hit count. This block combines the * resolve the move's total hit count. This block combines the
@ -228,9 +240,11 @@ export class MoveEffectPhase extends PokemonPhase {
* If the move missed a target, stop all future hits against that target * If the move missed a target, stop all future hits against that target
* and move on to the next target (if there is one). * and move on to the next target (if there is one).
*/ */
if (isCommanding || (!isImmune && !isProtected && !targetHitChecks[target.getBattlerIndex()])) { if (target.switchOutStatus || isCommanding || (!isImmune && !isProtected && !targetHitChecks[target.getBattlerIndex()])) {
this.stopMultiHit(target); this.stopMultiHit(target);
if (!target.switchOutStatus) {
this.scene.queueMessage(i18next.t("battle:attackMissed", { pokemonNameWithAffix: getPokemonNameWithAffix(target) })); this.scene.queueMessage(i18next.t("battle:attackMissed", { pokemonNameWithAffix: getPokemonNameWithAffix(target) }));
}
if (moveHistoryEntry.result === MoveResult.PENDING) { if (moveHistoryEntry.result === MoveResult.PENDING) {
moveHistoryEntry.result = MoveResult.MISS; moveHistoryEntry.result = MoveResult.MISS;
} }
@ -299,10 +313,17 @@ export class MoveEffectPhase extends PokemonPhase {
*/ */
if (lastHit) { if (lastHit) {
this.scene.triggerPokemonFormChange(user, SpeciesFormChangePostMoveTrigger); this.scene.triggerPokemonFormChange(user, SpeciesFormChangePostMoveTrigger);
/**
* Multi-Lens, Multi Hit move and Parental Bond check for PostDamageAbAttr
* other damage source are calculated in damageAndUpdate in pokemon.ts
*/
if (user.turnData.hitCount > 1) {
applyPostDamageAbAttrs(PostDamageAbAttr, target, 0, target.hasPassive(), false, [], user);
}
} }
/** /**
* Create a Promise that applys *all* effects from the invoked move's MoveEffectAttrs. * Create a Promise that applies *all* effects from the invoked move's MoveEffectAttrs.
* These are ordered by trigger type (see {@linkcode MoveEffectTrigger}), and each trigger * These are ordered by trigger type (see {@linkcode MoveEffectTrigger}), and each trigger
* type requires different conditions to be met with respect to the move's hit result. * type requires different conditions to be met with respect to the move's hit result.
*/ */

View File

@ -529,7 +529,7 @@ export class MovePhase extends BattlePhase {
* Displays the move's usage text to the player, unless it's a charge turn (ie: {@link Moves.SOLAR_BEAM Solar Beam}), * Displays the move's usage text to the player, unless it's a charge turn (ie: {@link Moves.SOLAR_BEAM Solar Beam}),
* the pokemon is on a recharge turn (ie: {@link Moves.HYPER_BEAM Hyper Beam}), or a 2-turn move was interrupted (ie: {@link Moves.FLY Fly}). * the pokemon is on a recharge turn (ie: {@link Moves.HYPER_BEAM Hyper Beam}), or a 2-turn move was interrupted (ie: {@link Moves.FLY Fly}).
*/ */
protected showMoveText(): void { public showMoveText(): void {
if (this.move.moveId === Moves.NONE) { if (this.move.moveId === Moves.NONE) {
return; return;
} }
@ -545,7 +545,7 @@ export class MovePhase extends BattlePhase {
applyMoveAttrs(PreMoveMessageAttr, this.pokemon, this.pokemon.getOpponents()[0], this.move.getMove()); applyMoveAttrs(PreMoveMessageAttr, this.pokemon, this.pokemon.getOpponents()[0], this.move.getMove());
} }
protected showFailedText(failedText?: string): void { public showFailedText(failedText?: string): void {
this.scene.queueMessage(failedText ?? i18next.t("battle:attackFailed")); this.scene.queueMessage(failedText ?? i18next.t("battle:attackFailed"));
} }
} }

View File

@ -21,8 +21,9 @@ export class PokemonHealPhase extends CommonAnimPhase {
private revive: boolean; private revive: boolean;
private healStatus: boolean; private healStatus: boolean;
private preventFullHeal: boolean; private preventFullHeal: boolean;
private fullRestorePP: boolean;
constructor(scene: BattleScene, battlerIndex: BattlerIndex, hpHealed: integer, message: string | null, showFullHpMessage: boolean, skipAnim: boolean = false, revive: boolean = false, healStatus: boolean = false, preventFullHeal: boolean = false) { constructor(scene: BattleScene, battlerIndex: BattlerIndex, hpHealed: integer, message: string | null, showFullHpMessage: boolean, skipAnim: boolean = false, revive: boolean = false, healStatus: boolean = false, preventFullHeal: boolean = false, fullRestorePP: boolean = false) {
super(scene, battlerIndex, undefined, CommonAnim.HEALTH_UP); super(scene, battlerIndex, undefined, CommonAnim.HEALTH_UP);
this.hpHealed = hpHealed; this.hpHealed = hpHealed;
@ -32,6 +33,7 @@ export class PokemonHealPhase extends CommonAnimPhase {
this.revive = revive; this.revive = revive;
this.healStatus = healStatus; this.healStatus = healStatus;
this.preventFullHeal = preventFullHeal; this.preventFullHeal = preventFullHeal;
this.fullRestorePP = fullRestorePP;
} }
start() { start() {
@ -86,6 +88,13 @@ export class PokemonHealPhase extends CommonAnimPhase {
lastStatusEffect = pokemon.status.effect; lastStatusEffect = pokemon.status.effect;
pokemon.resetStatus(); pokemon.resetStatus();
} }
if (this.fullRestorePP) {
for (const move of this.getPokemon().getMoveset()) {
if (move) {
move.ppUsed = 0;
}
}
}
pokemon.updateInfo().then(() => super.end()); pokemon.updateInfo().then(() => super.end());
} else if (this.healStatus && !this.revive && pokemon.status) { } else if (this.healStatus && !this.revive && pokemon.status) {
lastStatusEffect = pokemon.status.effect; lastStatusEffect = pokemon.status.effect;

View File

@ -27,9 +27,12 @@ export class PostSummonPhase extends PokemonPhase {
pokemon.lapseTag(BattlerTagType.MYSTERY_ENCOUNTER_POST_SUMMON); pokemon.lapseTag(BattlerTagType.MYSTERY_ENCOUNTER_POST_SUMMON);
} }
applyPostSummonAbAttrs(PostSummonAbAttr, pokemon).then(() => this.end()); applyPostSummonAbAttrs(PostSummonAbAttr, pokemon)
.then(() => {
const field = pokemon.isPlayer() ? this.scene.getPlayerField() : this.scene.getEnemyField(); const field = pokemon.isPlayer() ? this.scene.getPlayerField() : this.scene.getEnemyField();
field.forEach((p) => applyAbAttrs(CommanderAbAttr, p, null, false)); field.forEach((p) => applyAbAttrs(CommanderAbAttr, p, null, false));
this.end();
});
} }
} }

View File

@ -16,7 +16,7 @@ export class PostTurnStatusEffectPhase extends PokemonPhase {
start() { start() {
const pokemon = this.getPokemon(); const pokemon = this.getPokemon();
if (pokemon?.isActive(true) && pokemon.status && pokemon.status.isPostTurn()) { if (pokemon?.isActive(true) && pokemon.status && pokemon.status.isPostTurn() && !pokemon.switchOutStatus) {
pokemon.status.incrementTurn(); pokemon.status.incrementTurn();
const cancelled = new Utils.BooleanHolder(false); const cancelled = new Utils.BooleanHolder(false);
applyAbAttrs(BlockNonDirectDamageAbAttr, pokemon, cancelled); applyAbAttrs(BlockNonDirectDamageAbAttr, pokemon, cancelled);

View File

@ -43,7 +43,12 @@ export class QuietFormChangePhase extends BattlePhase {
const getPokemonSprite = () => { const getPokemonSprite = () => {
const sprite = this.scene.addPokemonSprite(this.pokemon, this.pokemon.x + this.pokemon.getSprite().x, this.pokemon.y + this.pokemon.getSprite().y, "pkmn__sub"); const sprite = this.scene.addPokemonSprite(this.pokemon, this.pokemon.x + this.pokemon.getSprite().x, this.pokemon.y + this.pokemon.getSprite().y, "pkmn__sub");
sprite.setOrigin(0.5, 1); sprite.setOrigin(0.5, 1);
sprite.play(this.pokemon.getBattleSpriteKey()).stop(); const spriteKey = this.pokemon.getBattleSpriteKey();
try {
sprite.play(spriteKey).stop();
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
sprite.setPipeline(this.scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(this.pokemon.getTeraType()) }); sprite.setPipeline(this.scene.spritePipeline, { tone: [ 0.0, 0.0, 0.0, 0.0 ], hasShadow: false, teraColor: getTypeRgb(this.pokemon.getTeraType()) });
[ "spriteColors", "fusionSpriteColors" ].map(k => { [ "spriteColors", "fusionSpriteColors" ].map(k => {
if (this.pokemon.summonData?.speciesForm) { if (this.pokemon.summonData?.speciesForm) {
@ -81,7 +86,12 @@ export class QuietFormChangePhase extends BattlePhase {
this.pokemon.setVisible(false); this.pokemon.setVisible(false);
this.pokemon.changeForm(this.formChange).then(() => { this.pokemon.changeForm(this.formChange).then(() => {
pokemonFormTintSprite.setScale(0.01); pokemonFormTintSprite.setScale(0.01);
pokemonFormTintSprite.play(this.pokemon.getBattleSpriteKey()).stop(); const spriteKey = this.pokemon.getBattleSpriteKey();
try {
pokemonFormTintSprite.play(spriteKey).stop();
} catch (err: unknown) {
console.error(`Failed to play animation for ${spriteKey}`, err);
}
pokemonFormTintSprite.setVisible(true); pokemonFormTintSprite.setVisible(true);
this.scene.tweens.add({ this.scene.tweens.add({
targets: pokemonTintSprite, targets: pokemonTintSprite,

View File

@ -3,6 +3,7 @@ import PartyUiHandler, { PartyOption, PartyUiMode } from "#app/ui/party-ui-handl
import { Mode } from "#app/ui/ui"; import { Mode } from "#app/ui/ui";
import { SwitchType } from "#enums/switch-type"; import { SwitchType } from "#enums/switch-type";
import { BattlePhase } from "./battle-phase"; import { BattlePhase } from "./battle-phase";
import { PostSummonPhase } from "./post-summon-phase";
import { SwitchSummonPhase } from "./switch-summon-phase"; import { SwitchSummonPhase } from "./switch-summon-phase";
/** /**
@ -63,6 +64,9 @@ export class SwitchPhase extends BattlePhase {
this.scene.ui.setMode(Mode.PARTY, this.isModal ? PartyUiMode.FAINT_SWITCH : PartyUiMode.POST_BATTLE_SWITCH, fieldIndex, (slotIndex: integer, option: PartyOption) => { this.scene.ui.setMode(Mode.PARTY, this.isModal ? PartyUiMode.FAINT_SWITCH : PartyUiMode.POST_BATTLE_SWITCH, fieldIndex, (slotIndex: integer, option: PartyOption) => {
if (slotIndex >= this.scene.currentBattle.getBattlerCount() && slotIndex < 6) { if (slotIndex >= this.scene.currentBattle.getBattlerCount() && slotIndex < 6) {
// Remove any pre-existing PostSummonPhase under the same field index.
// Pre-existing PostSummonPhases may occur when this phase is invoked during a prompt to switch at the start of a wave.
this.scene.tryRemovePhase(p => p instanceof PostSummonPhase && p.player && p.fieldIndex === this.fieldIndex);
const switchType = (option === PartyOption.PASS_BATON) ? SwitchType.BATON_PASS : this.switchType; const switchType = (option === PartyOption.PASS_BATON) ? SwitchType.BATON_PASS : this.switchType;
this.scene.unshiftPhase(new SwitchSummonPhase(this.scene, switchType, fieldIndex, slotIndex, this.doReturn)); this.scene.unshiftPhase(new SwitchSummonPhase(this.scene, switchType, fieldIndex, slotIndex, this.doReturn));
} }

View File

@ -1,5 +1,5 @@
import BattleScene from "#app/battle-scene"; import BattleScene from "#app/battle-scene";
import { applyPreSummonAbAttrs, applyPreSwitchOutAbAttrs, PreSummonAbAttr, PreSwitchOutAbAttr } from "#app/data/ability"; import { applyPreSummonAbAttrs, applyPreSwitchOutAbAttrs, PostDamageForceSwitchAbAttr, PreSummonAbAttr, PreSwitchOutAbAttr } from "#app/data/ability";
import { allMoves, ForceSwitchOutAttr } from "#app/data/move"; import { allMoves, ForceSwitchOutAttr } from "#app/data/move";
import { getPokeballTintColor } from "#app/data/pokeball"; import { getPokeballTintColor } from "#app/data/pokeball";
import { SpeciesFormChangeActiveTrigger } from "#app/data/pokemon-forms"; import { SpeciesFormChangeActiveTrigger } from "#app/data/pokemon-forms";
@ -167,10 +167,11 @@ export class SwitchSummonPhase extends SummonPhase {
const currentCommand = pokemon.scene.currentBattle.turnCommands[this.fieldIndex]?.command; const currentCommand = pokemon.scene.currentBattle.turnCommands[this.fieldIndex]?.command;
const lastPokemonIsForceSwitchedAndNotFainted = lastUsedMove?.hasAttr(ForceSwitchOutAttr) && !this.lastPokemon.isFainted(); const lastPokemonIsForceSwitchedAndNotFainted = lastUsedMove?.hasAttr(ForceSwitchOutAttr) && !this.lastPokemon.isFainted();
const lastPokemonHasForceSwitchAbAttr = this.lastPokemon.hasAbilityWithAttr(PostDamageForceSwitchAbAttr) && !this.lastPokemon.isFainted();
// Compensate for turn spent summoning // Compensate for turn spent summoning
// Or compensate for force switch move if switched out pokemon is not fainted // Or compensate for force switch move if switched out pokemon is not fainted
if (currentCommand === Command.POKEMON || lastPokemonIsForceSwitchedAndNotFainted) { if (currentCommand === Command.POKEMON || lastPokemonIsForceSwitchedAndNotFainted || lastPokemonHasForceSwitchAbAttr) {
pokemon.battleSummonData.turnCount--; pokemon.battleSummonData.turnCount--;
pokemon.battleSummonData.waveTurnCount--; pokemon.battleSummonData.waveTurnCount--;
} }

View File

@ -9,6 +9,8 @@ import { BattlePhase } from "./battle-phase";
import { ModifierRewardPhase } from "./modifier-reward-phase"; import { ModifierRewardPhase } from "./modifier-reward-phase";
import { MoneyRewardPhase } from "./money-reward-phase"; import { MoneyRewardPhase } from "./money-reward-phase";
import { TrainerSlot } from "#app/data/trainer-config"; import { TrainerSlot } from "#app/data/trainer-config";
import { Biome } from "#app/enums/biome";
import { achvs } from "#app/system/achv";
export class TrainerVictoryPhase extends BattlePhase { export class TrainerVictoryPhase extends BattlePhase {
constructor(scene: BattleScene) { constructor(scene: BattleScene) {
@ -34,11 +36,17 @@ export class TrainerVictoryPhase extends BattlePhase {
} }
const trainerType = this.scene.currentBattle.trainer?.config.trainerType!; // TODO: is this bang correct? const trainerType = this.scene.currentBattle.trainer?.config.trainerType!; // TODO: is this bang correct?
// Validate Voucher for boss trainers
if (vouchers.hasOwnProperty(TrainerType[trainerType])) { if (vouchers.hasOwnProperty(TrainerType[trainerType])) {
if (!this.scene.validateVoucher(vouchers[TrainerType[trainerType]]) && this.scene.currentBattle.trainer?.config.isBoss) { if (!this.scene.validateVoucher(vouchers[TrainerType[trainerType]]) && this.scene.currentBattle.trainer?.config.isBoss) {
this.scene.unshiftPhase(new ModifierRewardPhase(this.scene, [ modifierTypes.VOUCHER, modifierTypes.VOUCHER, modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PREMIUM ][vouchers[TrainerType[trainerType]].voucherType])); this.scene.unshiftPhase(new ModifierRewardPhase(this.scene, [ modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PREMIUM ][vouchers[TrainerType[trainerType]].voucherType]));
} }
} }
// Breeders in Space achievement
if (this.scene.arena.biomeType === Biome.SPACE
&& (trainerType === TrainerType.BREEDER || trainerType === TrainerType.EXPERT_POKEMON_BREEDER)) {
this.scene.validateAchv(achvs.BREEDERS_IN_SPACE);
}
this.scene.ui.showText(i18next.t("battle:trainerDefeated", { trainerName: this.scene.currentBattle.trainer?.getName(TrainerSlot.NONE, true) }), null, () => { this.scene.ui.showText(i18next.t("battle:trainerDefeated", { trainerName: this.scene.currentBattle.trainer?.getName(TrainerSlot.NONE, true) }), null, () => {
const victoryMessages = this.scene.currentBattle.trainer?.getVictoryMessages()!; // TODO: is this bang correct? const victoryMessages = this.scene.currentBattle.trainer?.getVictoryMessages()!; // TODO: is this bang correct?

View File

@ -23,6 +23,7 @@ export class TurnEndPhase extends FieldPhase {
this.scene.eventTarget.dispatchEvent(new TurnEndEvent(this.scene.currentBattle.turn)); this.scene.eventTarget.dispatchEvent(new TurnEndEvent(this.scene.currentBattle.turn));
const handlePokemon = (pokemon: Pokemon) => { const handlePokemon = (pokemon: Pokemon) => {
if (!pokemon.switchOutStatus) {
pokemon.lapseTags(BattlerTagLapseType.TURN_END); pokemon.lapseTags(BattlerTagLapseType.TURN_END);
this.scene.applyModifiers(TurnHealModifier, pokemon.isPlayer(), pokemon); this.scene.applyModifiers(TurnHealModifier, pokemon.isPlayer(), pokemon);
@ -38,6 +39,7 @@ export class TurnEndPhase extends FieldPhase {
} }
applyPostTurnAbAttrs(PostTurnAbAttr, pokemon); applyPostTurnAbAttrs(PostTurnAbAttr, pokemon);
}
this.scene.applyModifiers(TurnStatusEffectModifier, pokemon.isPlayer(), pokemon); this.scene.applyModifiers(TurnStatusEffectModifier, pokemon.isPlayer(), pokemon);

View File

@ -41,7 +41,7 @@ export class VictoryPhase extends PokemonPhase {
} }
if (!this.scene.getEnemyParty().find(p => this.scene.currentBattle.battleType === BattleType.WILD ? p.isOnField() : !p?.isFainted(true))) { if (!this.scene.getEnemyParty().find(p => this.scene.currentBattle.battleType === BattleType.WILD ? p.isOnField() : !p?.isFainted(true))) {
this.scene.pushPhase(new BattleEndPhase(this.scene)); this.scene.pushPhase(new BattleEndPhase(this.scene, true));
if (this.scene.currentBattle.battleType === BattleType.TRAINER) { if (this.scene.currentBattle.battleType === BattleType.TRAINER) {
this.scene.pushPhase(new TrainerVictoryPhase(this.scene)); this.scene.pushPhase(new TrainerVictoryPhase(this.scene));
} }

View File

@ -51,7 +51,7 @@ export class WeatherEffectPhase extends CommonAnimPhase {
}; };
this.executeForAll((pokemon: Pokemon) => { this.executeForAll((pokemon: Pokemon) => {
const immune = !pokemon || !!pokemon.getTypes(true, true).filter(t => this.weather?.isTypeDamageImmune(t)).length; const immune = !pokemon || !!pokemon.getTypes(true, true).filter(t => this.weather?.isTypeDamageImmune(t)).length || pokemon.switchOutStatus;
if (!immune) { if (!immune) {
inflictDamage(pokemon); inflictDamage(pokemon);
} }
@ -59,8 +59,12 @@ export class WeatherEffectPhase extends CommonAnimPhase {
} }
} }
this.scene.ui.showText(getWeatherLapseMessage(this.weather.weatherType)!, null, () => { // TODO: is this bang correct? this.scene.ui.showText(getWeatherLapseMessage(this.weather.weatherType) ?? "", null, () => {
this.executeForAll((pokemon: Pokemon) => applyPostWeatherLapseAbAttrs(PostWeatherLapseAbAttr, pokemon, this.weather)); this.executeForAll((pokemon: Pokemon) => {
if (!pokemon.switchOutStatus) {
applyPostWeatherLapseAbAttrs(PostWeatherLapseAbAttr, pokemon, this.weather);
}
});
super.start(); super.start();
}); });

View File

@ -358,7 +358,7 @@ export const achvs = {
MONO_FAIRY: new ChallengeAchv("MONO_FAIRY", "", "MONO_FAIRY.description", "fairy_feather", 100, (c, scene) => c instanceof SingleTypeChallenge && c.value === 18 && !scene.gameMode.challenges.some(c => c.id === Challenges.INVERSE_BATTLE && c.value > 0)), MONO_FAIRY: new ChallengeAchv("MONO_FAIRY", "", "MONO_FAIRY.description", "fairy_feather", 100, (c, scene) => c instanceof SingleTypeChallenge && c.value === 18 && !scene.gameMode.challenges.some(c => c.id === Challenges.INVERSE_BATTLE && c.value > 0)),
FRESH_START: new ChallengeAchv("FRESH_START", "", "FRESH_START.description", "reviver_seed", 100, (c, scene) => c instanceof FreshStartChallenge && c.value > 0 && !scene.gameMode.challenges.some(c => c.id === Challenges.INVERSE_BATTLE && c.value > 0)), FRESH_START: new ChallengeAchv("FRESH_START", "", "FRESH_START.description", "reviver_seed", 100, (c, scene) => c instanceof FreshStartChallenge && c.value > 0 && !scene.gameMode.challenges.some(c => c.id === Challenges.INVERSE_BATTLE && c.value > 0)),
INVERSE_BATTLE: new ChallengeAchv("INVERSE_BATTLE", "", "INVERSE_BATTLE.description", "inverse", 100, c => c instanceof InverseBattleChallenge && c.value > 0), INVERSE_BATTLE: new ChallengeAchv("INVERSE_BATTLE", "", "INVERSE_BATTLE.description", "inverse", 100, c => c instanceof InverseBattleChallenge && c.value > 0),
BREEDERS_IN_SPACE: new Achv("BREEDERS_IN_SPACE", "", "BREEDERS_IN_SPACE.description", "moon_stone", 100).setSecret(), BREEDERS_IN_SPACE: new Achv("BREEDERS_IN_SPACE", "", "BREEDERS_IN_SPACE.description", "moon_stone", 50).setSecret(),
}; };
export function initAchievements() { export function initAchievements() {

View File

@ -171,7 +171,7 @@ export default class PokemonData {
playerPokemon.nickname = this.nickname; playerPokemon.nickname = this.nickname;
} }
}) })
: scene.addEnemyPokemon(species, this.level, battleType === BattleType.TRAINER ? !double || !(partyMemberIndex % 2) ? TrainerSlot.TRAINER : TrainerSlot.TRAINER_PARTNER : TrainerSlot.NONE, this.boss, this); : scene.addEnemyPokemon(species, this.level, battleType === BattleType.TRAINER ? !double || !(partyMemberIndex % 2) ? TrainerSlot.TRAINER : TrainerSlot.TRAINER_PARTNER : TrainerSlot.NONE, this.boss, false, this);
if (this.summonData) { if (this.summonData) {
ret.primeSummonData(this.summonData); ret.primeSummonData(this.summonData);
} }

View File

@ -1,9 +1,9 @@
import { Mode } from "#app/ui/ui"; import { Mode } from "#app/ui/ui";
import i18next from "i18next"; import i18next from "i18next";
import BattleScene from "../../battle-scene"; import BattleScene from "#app/battle-scene";
import { hasTouchscreen } from "../../touch-controls"; import { hasTouchscreen } from "#app/touch-controls";
import { updateWindowType } from "../../ui/ui-theme"; import { updateWindowType } from "#app/ui/ui-theme";
import { CandyUpgradeNotificationChangedEvent } from "../../events/battle-scene"; import { CandyUpgradeNotificationChangedEvent } from "#app/events/battle-scene";
import SettingsUiHandler from "#app/ui/settings/settings-ui-handler"; import SettingsUiHandler from "#app/ui/settings/settings-ui-handler";
import { EaseType } from "#enums/ease-type"; import { EaseType } from "#enums/ease-type";
import { MoneyFormat } from "#enums/money-format"; import { MoneyFormat } from "#enums/money-format";
@ -44,6 +44,7 @@ const OFF_ON: SettingOption[] = [
label: i18next.t("settings:on") label: i18next.t("settings:on")
} }
]; ];
const AUTO_DISABLED: SettingOption[] = [ const AUTO_DISABLED: SettingOption[] = [
{ {
value: "Auto", value: "Auto",
@ -55,6 +56,19 @@ const AUTO_DISABLED: SettingOption[] = [
} }
]; ];
const TOUCH_CONTROLS_OPTIONS: SettingOption[] = [
{
value: "Auto",
label: i18next.t("settings:auto")
},
{
value: "Disabled",
label: i18next.t("settings:disabled"),
needConfirmation: true,
confirmationMessage: i18next.t("settings:confirmDisableTouch")
}
];
const SHOP_CURSOR_TARGET_OPTIONS: SettingOption[] = [ const SHOP_CURSOR_TARGET_OPTIONS: SettingOption[] = [
{ {
value: "Rewards", value: "Rewards",
@ -100,7 +114,9 @@ export enum SettingType {
type SettingOption = { type SettingOption = {
value: string, value: string,
label: string label: string,
needConfirmation?: boolean,
confirmationMessage?: string
}; };
export interface Setting { export interface Setting {
@ -344,13 +360,6 @@ export const Setting: Array<Setting> = [
default: 1, default: 1,
type: SettingType.GENERAL type: SettingType.GENERAL
}, },
{
key: SettingKeys.Touch_Controls,
label: i18next.t("settings:touchControls"),
options: AUTO_DISABLED,
default: 0,
type: SettingType.GENERAL
},
{ {
key: SettingKeys.Vibration, key: SettingKeys.Vibration,
label: i18next.t("settings:vibrations"), label: i18next.t("settings:vibrations"),
@ -358,6 +367,28 @@ export const Setting: Array<Setting> = [
default: 0, default: 0,
type: SettingType.GENERAL type: SettingType.GENERAL
}, },
{
key: SettingKeys.Touch_Controls,
label: i18next.t("settings:touchControls"),
options: TOUCH_CONTROLS_OPTIONS,
default: 0,
type: SettingType.GENERAL,
isHidden: () => !hasTouchscreen()
},
{
key: SettingKeys.Move_Touch_Controls,
label: i18next.t("settings:moveTouchControls"),
options: [
{
value: "Configure",
label: i18next.t("settings:change")
}
],
default: 0,
type: SettingType.GENERAL,
activatable: true,
isHidden: () => !hasTouchscreen()
},
{ {
key: SettingKeys.Language, key: SettingKeys.Language,
label: i18next.t("settings:language"), label: i18next.t("settings:language"),
@ -643,20 +674,6 @@ export const Setting: Array<Setting> = [
type: SettingType.AUDIO, type: SettingType.AUDIO,
requireReload: true requireReload: true
}, },
{
key: SettingKeys.Move_Touch_Controls,
label: i18next.t("settings:moveTouchControls"),
options: [
{
value: "Configure",
label: i18next.t("settings:change")
}
],
default: 0,
type: SettingType.GENERAL,
activatable: true,
isHidden: () => !hasTouchscreen()
},
{ {
key: SettingKeys.Shop_Cursor_Target, key: SettingKeys.Shop_Cursor_Target,
label: i18next.t("settings:shopCursorTarget"), label: i18next.t("settings:shopCursorTarget"),
@ -849,7 +866,7 @@ export function setSetting(scene: BattleScene, setting: string, value: integer):
if (scene.ui) { if (scene.ui) {
const cancelHandler = () => { const cancelHandler = () => {
scene.ui.revertMode(); scene.ui.revertMode();
(scene.ui.getHandler() as SettingsUiHandler).setOptionCursor(0, 0, true); (scene.ui.getHandler() as SettingsUiHandler).setOptionCursor(-1, 0, true);
}; };
const changeLocaleHandler = (locale: string): boolean => { const changeLocaleHandler = (locale: string): boolean => {
try { try {

View File

@ -0,0 +1,81 @@
import { BattlerIndex } from "#app/battle";
import { isBetween, toDmgValue } from "#app/utils";
import { Abilities } from "#enums/abilities";
import { Moves } from "#enums/moves";
import { Species } from "#enums/species";
import GameManager from "#test/utils/gameManager";
import Phaser from "phaser";
import { afterEach, beforeAll, beforeEach, describe, expect, it } from "vitest";
describe("Abilities - Analytic", () => {
let phaserGame: Phaser.Game;
let game: GameManager;
beforeAll(() => {
phaserGame = new Phaser.Game({
type: Phaser.HEADLESS,
});
});
afterEach(() => {
game.phaseInterceptor.restoreOg();
});
beforeEach(() => {
game = new GameManager(phaserGame);
game.override
.moveset([ Moves.SPLASH, Moves.TACKLE ])
.ability(Abilities.ANALYTIC)
.battleType("single")
.disableCrits()
.startingLevel(200)
.enemyLevel(200)
.enemySpecies(Species.SNORLAX)
.enemyAbility(Abilities.BALL_FETCH)
.enemyMoveset(Moves.SPLASH);
});
it("should increase damage if the user moves last", async () => {
await game.classicMode.startBattle([ Species.ARCEUS ]);
const enemy = game.scene.getEnemyPokemon()!;
game.move.select(Moves.TACKLE);
await game.setTurnOrder([ BattlerIndex.PLAYER, BattlerIndex.ENEMY ]);
await game.toNextTurn();
const damage1 = enemy.getInverseHp();
enemy.hp = enemy.getMaxHp();
game.move.select(Moves.TACKLE);
await game.setTurnOrder([ BattlerIndex.ENEMY, BattlerIndex.PLAYER ]);
await game.phaseInterceptor.to("BerryPhase");
expect(isBetween(enemy.getInverseHp(), toDmgValue(damage1 * 1.3) - 3, toDmgValue(damage1 * 1.3) + 3)).toBe(true);
});
it("should increase damage only if the user moves last in doubles", async () => {
game.override.battleType("double");
await game.classicMode.startBattle([ Species.GENGAR, Species.SHUCKLE ]);
const [ enemy, ] = game.scene.getEnemyField();
game.move.select(Moves.TACKLE, 0, BattlerIndex.ENEMY);
game.move.select(Moves.SPLASH, 1);
await game.setTurnOrder([ BattlerIndex.PLAYER, BattlerIndex.PLAYER_2, BattlerIndex.ENEMY, BattlerIndex.ENEMY_2 ]);
await game.toNextTurn();
const damage1 = enemy.getInverseHp();
enemy.hp = enemy.getMaxHp();
game.move.select(Moves.TACKLE, 0, BattlerIndex.ENEMY);
game.move.select(Moves.SPLASH, 1);
await game.setTurnOrder([ BattlerIndex.PLAYER_2, BattlerIndex.ENEMY, BattlerIndex.ENEMY_2, BattlerIndex.PLAYER ]);
await game.toNextTurn();
expect(isBetween(enemy.getInverseHp(), toDmgValue(damage1 * 1.3) - 3, toDmgValue(damage1 * 1.3) + 3)).toBe(true);
enemy.hp = enemy.getMaxHp();
game.move.select(Moves.TACKLE, 0, BattlerIndex.ENEMY);
game.move.select(Moves.SPLASH, 1);
await game.setTurnOrder([ BattlerIndex.PLAYER_2, BattlerIndex.ENEMY, BattlerIndex.PLAYER, BattlerIndex.ENEMY_2 ]);
await game.phaseInterceptor.to("BerryPhase");
expect(enemy.getInverseHp()).toBe(damage1);
});
});

View File

@ -1,9 +1,10 @@
import { allAbilities } from "#app/data/ability";
import { Abilities } from "#enums/abilities"; import { Abilities } from "#enums/abilities";
import { Moves } from "#enums/moves"; import { Moves } from "#enums/moves";
import { Species } from "#enums/species"; import { Species } from "#enums/species";
import GameManager from "#test/utils/gameManager"; import GameManager from "#test/utils/gameManager";
import Phaser from "phaser"; import Phaser from "phaser";
import { afterEach, beforeAll, beforeEach, describe, it, expect } from "vitest"; import { afterEach, beforeAll, beforeEach, describe, it, expect, vi } from "vitest";
describe("Abilities - Arena Trap", () => { describe("Abilities - Arena Trap", () => {
let phaserGame: Phaser.Game; let phaserGame: Phaser.Game;
@ -55,4 +56,39 @@ describe("Abilities - Arena Trap", () => {
expect(game.scene.getEnemyField().length).toBe(2); expect(game.scene.getEnemyField().length).toBe(2);
}); });
/**
* This checks if the Player Pokemon is able to switch out/run away after the Enemy Pokemon with {@linkcode Abilities.ARENA_TRAP}
* is forcefully moved out of the field from moves such as Roar {@linkcode Moves.ROAR}
*
* Note: It should be able to switch out/run away
*/
it("should lift if pokemon with this ability leaves the field", async () => {
game.override
.battleType("double")
.enemyMoveset(Moves.SPLASH)
.moveset([ Moves.ROAR, Moves.SPLASH ])
.ability(Abilities.BALL_FETCH);
await game.classicMode.startBattle([ Species.MAGIKARP, Species.SUDOWOODO, Species.LUNATONE ]);
const [ enemy1, enemy2 ] = game.scene.getEnemyField();
const [ player1, player2 ] = game.scene.getPlayerField();
vi.spyOn(enemy1, "getAbility").mockReturnValue(allAbilities[Abilities.ARENA_TRAP]);
game.move.select(Moves.ROAR);
game.move.select(Moves.SPLASH, 1);
// This runs the fist command phase where the moves are selected
await game.toNextTurn();
// During the next command phase the player pokemons should not be trapped anymore
game.move.select(Moves.SPLASH);
game.move.select(Moves.SPLASH, 1);
await game.toNextTurn();
expect(player1.isTrapped()).toBe(false);
expect(player2.isTrapped()).toBe(false);
expect(enemy1.isOnField()).toBe(false);
expect(enemy2.isOnField()).toBe(true);
});
}); });

View File

@ -0,0 +1,74 @@
import type { CommandPhase } from "#app/phases/command-phase";
import { Command } from "#app/ui/command-ui-handler";
import { Abilities } from "#enums/abilities";
import { Moves } from "#enums/moves";
import { Species } from "#enums/species";
import GameManager from "#test/utils/gameManager";
import Phaser from "phaser";
import { afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
describe("Abilities - Honey Gather", () => {
let phaserGame: Phaser.Game;
let game: GameManager;
beforeAll(() => {
phaserGame = new Phaser.Game({
type: Phaser.HEADLESS,
});
});
afterEach(() => {
game.phaseInterceptor.restoreOg();
});
beforeEach(() => {
game = new GameManager(phaserGame);
game.override
.moveset([ Moves.SPLASH, Moves.ROAR, Moves.THUNDERBOLT ])
.startingLevel(100)
.ability(Abilities.HONEY_GATHER)
.passiveAbility(Abilities.RUN_AWAY)
.battleType("single")
.disableCrits()
.enemySpecies(Species.MAGIKARP)
.enemyAbility(Abilities.BALL_FETCH)
.enemyMoveset(Moves.SPLASH);
});
it("should give money when winning a battle", async () => {
await game.classicMode.startBattle([ Species.MILOTIC ]);
game.scene.money = 1000;
game.move.select(Moves.THUNDERBOLT);
await game.toNextWave();
expect(game.scene.money).toBeGreaterThan(1000);
});
it("should not give money when the enemy pokemon flees", async () => {
await game.classicMode.startBattle([ Species.MILOTIC ]);
game.scene.money = 1000;
game.move.select(Moves.ROAR);
await game.toNextTurn();
expect(game.scene.money).toBe(1000);
expect(game.scene.currentBattle.waveIndex).toBe(2);
});
it("should not give money when the player flees", async () => {
await game.classicMode.startBattle([ Species.MILOTIC ]);
game.scene.money = 1000;
// something weird is going on with the test framework, so this is required to prevent a crash
const enemy = game.scene.getEnemyPokemon()!;
vi.spyOn(enemy, "scene", "get").mockReturnValue(game.scene);
const commandPhase = game.scene.getCurrentPhase() as CommandPhase;
commandPhase.handleCommand(Command.RUN, 0);
await game.toNextTurn();
expect(game.scene.money).toBe(1000);
expect(game.scene.currentBattle.waveIndex).toBe(2);
});
});

View File

@ -1,5 +1,5 @@
import { Type } from "#enums/type"; import { Type } from "#enums/type";
import { BattlerTagType } from "#app/enums/battler-tag-type"; import { BattlerTagType } from "#enums/battler-tag-type";
import { toDmgValue } from "#app/utils"; import { toDmgValue } from "#app/utils";
import { Abilities } from "#enums/abilities"; import { Abilities } from "#enums/abilities";
import { Moves } from "#enums/moves"; import { Moves } from "#enums/moves";
@ -8,7 +8,7 @@ import { Stat } from "#enums/stat";
import { StatusEffect } from "#enums/status-effect"; import { StatusEffect } from "#enums/status-effect";
import GameManager from "#test/utils/gameManager"; import GameManager from "#test/utils/gameManager";
import Phaser from "phaser"; import Phaser from "phaser";
import { afterEach, beforeAll, beforeEach, describe, expect, it } from "vitest"; import { afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
describe("Abilities - Parental Bond", () => { describe("Abilities - Parental Bond", () => {
@ -470,4 +470,25 @@ describe("Abilities - Parental Bond", () => {
expect(enemyPokemon.getStatStage(Stat.SPATK)).toBe(1); expect(enemyPokemon.getStatStage(Stat.SPATK)).toBe(1);
} }
); );
it("should not allow Future Sight to hit infinitely many times if the user switches out", async () => {
game.override.enemyLevel(1000)
.moveset(Moves.FUTURE_SIGHT);
await game.classicMode.startBattle([ Species.BULBASAUR, Species.CHARMANDER, Species.SQUIRTLE ]);
const enemyPokemon = game.scene.getEnemyPokemon()!;
vi.spyOn(enemyPokemon, "damageAndUpdate");
game.move.select(Moves.FUTURE_SIGHT);
await game.toNextTurn();
game.doSwitchPokemon(1);
await game.toNextTurn();
game.doSwitchPokemon(2);
await game.toNextTurn();
// TODO: Update hit count to 1 once Future Sight is fixed to not activate abilities if user is off the field
expect(enemyPokemon.damageAndUpdate).toHaveBeenCalledTimes(2);
});
}); });

Some files were not shown because too many files have changed in this diff Show More