Previously, the creating a new ViewPort loaded from 2 text files and creating a new HardcodeTablesMoel loaded from 1 text file. This is a lot of parsing!
Refactor to do the parsing once, in the EditorViewModel, using a Singleton class to hold the non-editable loaded data. Inject that data into the appropriate structers later on.
To prevent massive refactoring in the tests, not every ViewPort needs to be given a Singletons instance. Instead, allow a ViewPort to still do its own parsing. However, BaseViewModelTestClass has been updated to make this work for a majority of tests, along with changes to AutoSearchTests's fixture and several of the Setup methods that are used by multiple tests.
- Remove AutoSearchModel. We're not using it anymore. Move its constants to HardcodeTablesModel.
- Move constants from EggMoveRun to HardcodeTablesModel. Should've done this a while ago.
Other things should probably be in this reference file too, such as the headers, streams, and default lists. But this is a good start and should make it more expandable in the future.
Each of Ruby/Sapphire/FireRed/LeafGreen has a 1.1 version as well as the 1.0 version floating around online of the English GBA rom. I should be able to tell the difference between the two versions and load tables correctly.
This refactor makes it possible to tell the difference. Loading the tables correctly is coming next.
in thumb code, branch-link commands are relative. That means that the instruction for the same destination will look different depending on the source.
As a user, I want to know what thumb code calls a routine I'm looking at. That's most likely going to be via a branch-link command, although it could be through a blx. Let the user use Find -> "bl <someaddress>" to search for branch-links that jump to a given location.
* Added some default lists
* Lists are loaded/saved with the TOML file
* Tests showing that lists work right.
Lists can be used as text displays for enums/bit arrays. The difference is that lists aren't sourced from the ROM.
In FR/LG, there's a limiter built into special 397 (the move tutor special) that makes it behave differently after the element 14 (0-14 act one way, 15+ act a different way). I added a one-byte change to switch the branch condition to 'never'.
In order to do this, I needed to locate the special list, so I went ahead and added it to all the games, complete with a unit test to verify.
The specials table + Clover exposed a bug: when adding anchors from a table with an unknown pointer format, we need to clear the data of existing conflicting runs. Example: a text run that goes over the anchor isn't actually a text run.
this is the first top level custom stream, so there was some extra places where I needed to add cache scopes. Otherwise, this is a fairly straightforward change.
The TableStreamRun/LengthFromParentStreamStrategy/GetCount has trouble getting the Count correctly during the initial verification, since the parent table hasn't actually been added to the model yet. So GetCount needs access to both the parent table's segments and the name of the pointer field. This lets the LengthFromParentStrategy to math to figure out segment offsets without needing the parent to actually be in the model. This extra info is only needed during verification: it's ok if it's `null` once the run is already added, such as during `CompleteEditOperation` and `TableTool`.
Add verification logic so we can know that we found a reasonable number of multichoice for each test rom. DarkRising's data is bugged, so ignore that one.
The multichoice didn't load right for a number of reasons
* The PCS has a double-escape character that I wasn't handling right.
* The check to see if a value is correct should verify that the value doesn't look like a pointer (high-byte on a 4-byte value should be less than 0x08).
* Had the wrong source for FireRed: typo
* Inner formats weren't being verified correctly for added tables
There are 4 tables related to the pokedex that I'm adding here:
* regional dex: for each pokemon, what is its regional dex index
* national dex: for each pokemon, what is its national dex index
* conversion: for each regional dex entry, what index is it in the national dex (can be computed automatically, so I added a QuickEdit item)
* dex info, such as the dex description
I also updated App.xaml and MainWindow.xaml.cs to make the QuickEditItems look better.
* table format feature: allow for recursive table definitions, simply because it's shorter.
* include expected locations of pointers to the Evolution table
* unit tests to show that we found the evolution table correctly
* model bugfix: when specifying to keep pointers, don't clear them during unusual loading situations
* model bugfix: when adding a format to a pointer in a table, if that location is already a table, give up and leave the table there.
The first move has no move description. So the move desciptions table should be the same length as the move names table, minus one. Added support for this kind of concept.
change tracking was previously done in the model, but exposed in the ViewModel via a data format. The problem with this is that it meant that all changed formats were wrapped in a new format, which would require a lot of work to fully validate.
The new implementation is still in the model, but exposed in the ViewModel through a new property on the HexElement. The data formats are unchanged.
Well it's not pretty and it's not well tested, but the first phase of trainer pokemon teams is complete!
The trainer pokemon team (TPT) is both a table and a stream: it's a table of pokemon, but it's also editable as a stream. This lets me show a trainer's pokemon as part of the same table as the trainer, but you can dive down for table support.
Integer bounded fields work a lot like table-matched fields. But instead of having an option of every entry in the table, it's just an option of every entry less than the given number.
* Also moved `GetOptions` to `ModelCacheScope` since no one else is using it.
* Also updated `ArrayRunEnumSegment` to use cache scopes.
* trainerdata makes use of this feature
Trainer tables include a nested pointer, which works a bit weird because the pointer points to a different data structure depending on the `structType`. The structure is a table, but won't be named. Since that pointer will require some more changes, for now we're just adding the parent table - the trainers.
To facilitate faster editing, the table tool enums and bitarrays now include links to their sources. This should allow the user to jump to a source faster for when they want to add a new option to a list, such as adding a new type or a new item.
The AutoSearchModel is nifty, but seems to have trouble in a lot of situations where data isn't in the format I expect.
However, I've noticed that while many romhacks move tables around, a lot less of them move code around. So I can depend on most of the pointers to those tables still being in the same spot.
Based on this idea, I've created a new "HardcodeTablesModel" that uses known pointer locations to find tables instead of just searching for tables based on their format. This lets me simplify a lot of the logic, reducing it to basically a pointer lookup in many cases.
Most of the tests for FireRed are passing now using the new HardcodeTablesModel. I'll continue looking into issues from FireRed and the other baseroms in the next update.