Ty @CanoeHope !
Closes#2677
To edit these values, use the Block Data editor and select the *Object Trainer Card
Co-Authored-By: CanoeHope <canoehope@users.noreply.github.com>
Cuts out about half the size; there's still a bunch of apply-value logic but it's not really big enough for a separate class.
Rename BallRandomizer->BallApplicator
Traded eggs in gen4 can have from any game (since version isn't updated on hatch).
Use the hashsets, and remove the incorrect array. The incorrect array allowed stuff like Pokéwalker to be a "valid met location", hah.
held item list now allocates less (concat arrays instead of ienumerables)
item list already prunes out of range items, so simplify data source fetch
simplify item list prune (return as list, so we can call RemoveAll instead of Where.ToList)
Now matches Interface declaration style (iAccessorGenGame), and is consistently named with the other accessors already using the same naming style
plus they are now ordered in the file tree :)
no functional change
Not done for Array types or Object types
muh reflection, such spooky
mark Offset as non-browsable so it doesn't show up in propertygrid if the block is being edited by a grid :)
I imagine a struct-type-sensitive array property grid edit could be done via Buffer.BlockCopy to a dest array, but there's so few Array blocks... so meh
Uses reflection to grab a list of defined constants (block keys), and a list of defined block reader classes.
Show name of block in red for a more prominent hint that this block is somewhat editable :)
Closes#2658 ty @CanoeHope !
Mostly just serves as documentation; with the amount of fields being editable increasing, hard-coded GUI might not be optimal here. I'm thinking something like a PropertyGrid based on the selected block which will pull up the Block object if the key matches... for fields, something like a dynamically populated list or something.
Use reflection to grab all const declarations (private and public), and grab the name of that const. Whenever that block is mentioned in our diff, use the name instead of the key.
Helps identify what changed / remove noise if you don't care about that block.
gen7 used same as gen6, we just need to restrict gen!=8
add placeholder LGPE origin check; that'll likely throw a wrench into things when HOME happens (next month?).
Record ID const declaration for reuse
Change 255->300 for streak max
Set record as well (ignore currently set value if modified via dropdown)
Closes#2649
Not sure if Money and BP can get a similar record-set treatment.
sometimes competitive sets have multiple moves in one slot as optional coverage moves. Handle these cases by splitting and trimming over '/'. Example: https://pastebin.com/raw/jvPziRdC (The dusk mane set)
Apparently my copypaste of the class didn't delete all the old unused controls. Ha!
Move non-gui logic to core as separate classes, in case ppl wanted to reuse them in their own projects.
blank saves do not have the type metadata for the blocks that are spoofed, nor do they have all blocks spoofed.
I suspect things might get more difficult as more value-blocks are identified, which would throw a wrench into things. We'll figure that out at that time :)
Add a test to ensure that the blank save can be created correctly
Closes#2644
Blocks that use Bool1/2 toggle to the other state; evident when comparing between two different saves. The key doesn't change, only the Type is toggled.
Add more direct legality analysis constructors
evo count is >= 1
fix invalid test message
disallow gen2 moves if transferred from gen1
use ^1 instead of len-1 for netcore test project
Some routes use the evolutiontree directly instead of this method (with the same name); should probably consolidate but meh
This causes Shedinja to yield the correct evolution chain when called directly (because nothing naturally evolves to shedinja; it's created out of thin air as a clone)
Take the egg short circuit with it to keep things simple
Rather than storing a dictionary of keys, we can abuse the fact that the SCBlock[] is stored in order of ascending block key.
Binary Search doesn't require extra memory like a Dictionary would; also, we only need to find a few blocks.
blanks: {key,size}
fetch: get block by key (index isnt the same between patches, as blocks with different keys get added). The savefile stores them as a SortedDictionary (by key), hence the shifting.
USUM had 20 for both, but XY/AO/SM had only 1 (vivillon had 20); make
them consistent so that our generated evolution paths behave correctly
Add meowstic specific evolution form modifier... so silly
simpler to have it inlined with the sSpecies, for jit optimization
could probably do this with silvally but meh, things work fine now
Closes#2603
All logic in PokeCrypto is separate from the rest of the PKHeX.Core
library; makes it easy to just rip this portion out and reuse in other
projects without needing the entirety of PKHeX.Core logic
optimize out the CheckEncrypted to the actual path, separate methods.
Only usages of this method were with hardcoded Format values, so no
impact
PKX.Generation is 8, which returns SWSH evo tree; evo tree doesn't have
non-galar-native species data, so stuff like Ambipom don't get reversed
properly.
use math.max for tree fetch when appropriate:
- egg generator: pre-evolutions like pichu should be allowed if pk1
- don't fetch format twice, just do math.max
#2603
add in "secret" heal/healPP actions -- do ".Heal=$suggest" to refresh
all stats like it was healed at the pokecenter. I can't think of a good
way to handle invoking of methods (">", but what about parameters?)
Not going to implement this within the base repo as z3 is too large of a
dependency and is platform specific.
If anyone wants to implement as a plugin project, just inject your new
methods via the setters on the static func/action at the top of the 3
classes.
Since z3's searches aren't instant, I'd recommend caching recent results
in a dictionary, as re-parses are common. Something like the Wordfilter
is what you'd be aiming for :)
Closes#2617
Manually modified showdown sets can contain errors (capitalization,
etc). Use the string search api to permit weaker matches, since there's
not going to be any exact-matches-with-different-caps/spaces.
The nest is situated right next to the load line, and may be accessed
from either map (across the load line), resulting in a Dusty Bowl
Pumpkaboo-0.
Many thanks to Anubis on Discord for figuring this (very silly) thing
out !
Closes#2573
- self-hosted raids can be downleveled too (see cufant), probably only
by 1 rank
- min-rank check now checks for downleveled cases
- Add extra gyarados/ferrothorn locations
the "Strong" static encounters can be near-matches with wild encounter
slots; example is a evolved Cutiefly->Ribombee with Quiver Dance.
Remove unnecessary IsLink/FriendSafari check for this gen8 method
https://github.com/kwsch/PKHeX/issues/2573#issuecomment-569126371
SCBlock is an input to the individual save blocks; changing the SCBlock
byte[] reference won't change the individual save block reference. Just
copy the data and keep the original reference instead.
Repro: trainer data editor, save-close window, then delete a slot.
Export save; reload. Changes to box data were using old byte[]
reference, and didn't get repointed. Works fine with latest commit now.
I think I wanted to avoid copyto since it's slower than just a reference
change; but that didn't work out perfectly :)
Hold alt when hitting activate all to dump instead
I've seen DenType=5 Event=2 for at least one raid so far... not sure if
the event/rare properties are accurate.
Closes#2577 thanks @HoppyShnell ! -- this looks like the final met
location ID?!
Not sure if Murkrow (locked) is missing one; moved duplicate-location
Heracross and made it use the same locks.
just read the comments & code, this one is an annoying oversight
untraded pkm /should/ never have HT memory data, but sometimes it do be
like that
Closes#2571
Move EncounterOriginal to Legal info; needed in order to pass the
correct encounter to the EvoChain fetch.
The EncounterOriginal 'hack' might be unnecessary with the current state
of the legality checker... maybe can see if it can be removed later.
If the feeling is zero the game's string formatter will treat it as
null, and will newline before the period.
Gen6 (if I recall correctly) had "it was happy" as index 0
Gen8 (new) has "it was happy" as index 1, with 0 being invalid-bad.
Slice the array differently for gen8 to include the empty line as index
0.
Closes#2549 , ty @crzyc && @architdate for testing index 0 :)
.PID=$shiny0 will do squares
anything else will do stars
.RelearnMoves=$suggestAll will give ALL TR moves, not just the ones for
its current movepool.
.Ribbons=$suggest will give all valid ribbons
.Ribbons=$suggestNone will remove all ribbons (except required ones like
event ribbons)
Closes#2568
320 is max hp (31IV 252EV), is this just -60 from max HP (threshold to
evolve at?)
might need some more research to see what is going on with this
only trycatch in release builds; was confused until I stepped thru and
saw the crash
Rewrite a bunch of the history verification stuff
Fix a few test cases with incorrect OT Friendship (transferred), and
missing GeoCountry
Need to rewrite memory verification next
(All test cases currently pass)
#2545
GetDestinationForm for gen7+ is fine
gen7 and gen8 use the "form" argument as the destination form; -1 means
don't change
espurr-F just gets forced to 1 in gen7 since it's -1
Closes#2564 ty @iiippppk
only used for Zukan7b, but add in handling so that it works for <=gen6
games, and supports form alterations too!
update style to match GetPreEvolutions
could probably update this to yield tuples (species, form) but LGPE/SWSH
only needs species. If there's the need for tuples later, should be ez
tweak.
espurr-F evolves to form-1 from form0, even tho the form arg is -1 (gen7
consideration)
gen8 has 0/1 for the two evolutions, dictating the destination form
DexLevel was the initial abstraction, which was expanded/reused for
evolution details
I should probably merge the two classes since everything is passed as
EvoCriteria
The encounter generators do some silly form fuzzy match which can now be
more accurately checked since I've moved Form to DexLevel... maybe a
future commit can clean that up.
encounterarea2 was reusing this class, just use a throwaway readonly
struct as our temp value storage
- Use tail recursion and a lookup table (species | form) for reversing
- generate the reversal lookup by extrapolating all species-form
destination values (EvolutionLink)
All tests pass, and no special handling for forms is required. Kinda
suspicious that it works this simply...
Redo evolution banning (no wormhole for non-Alolan evolutions in SM), in
a style that we can ban the Gigantamax event evolutions
(pika/meowth/eevee). Their evolutions can't be resulted from a pre-evo,
because the in-game routine early aborts if the gigantamax flag is set
for those species.
Update gen4 personal tables (formCount was 0, needs to be a minimum of 1
by default)
Closes#2537
* update forme to showdown strings
Galarian is represented as Galar on PS!
Polteageist has no form atall
galarian now called Galar by default to match with Alola as a forme. changed darmanitan forme-strings in form converter. Added sinistea to the forme ignore list when converting to showdown
format >= 6 is always true (early return in entry)
don't double-flag/check memory presence in OTs from gen5 and below (hist
and OT verifier)
rename method; I'll probably rework the flow of things for gen6
verification and gen8 verification since the rules are slightly
different
Certain Mark values (ribbon) are only obtainable if the encounter was
obtained in some weather (I really hope there's no crossover cases for
this), and non-symbol encounters can't wander to another zone.
I wonder if you can wander from one zone with one exclusive weather, to
another zone, and get an 'unobtainable' mark (with the new zone's
weather) on the crossover mon's weather. yikes lmao
yeah your initial hacks were hacks
It appears there's a bug (in the game) for link trade memories --
applied to the OT memory instead of HT memory?? Fun!
Closes#2525
G4Celebi & G6Link met location match; Pokémon Link was only available
for Gen6 so just check for that origin.
Ty @Ammako
tbh I shouldn't even have this property ha
Private report with 3 specimens, 2 undocumented met locations
The other was a Gigantamax which matched another static encounter,
resulting in a partial match being accepted (the real match came after,
but was never iterated to).
Rather than adding deferrals for Enc8, do nest stuff first since it's
the most restrictive
In the past we didn't really have duplicate static encounters with
slightly different permissions.
Thanks @ReignOfComputer & {reporting user}!