Move the DryCostWriter (and Sanity Checkes) out of the Main Menu startup
Lisias opened this issue · 3 comments
On heavily loaded rigs, the CoRoutine stunt is bitting due the frames being lost in the process.
To where and how to do it is an exercise to the implementer. Good luck.
Whole history:
Since 1.5.x (I think) once we load a savegame, KSP will happily apply to any living flying craft any changes detected on the GameDatabase (removing missing PartModules, and injecting default values for new ones that were not present last time the savegame was written). This is bless, as it allows to safely (most of the time, some caveats were found) install new Add'Ons on our GameData without loosing our savegames (hopefully), but it can also be a curse on some borderline situations.
And I was thrown under the bus by one of these borderline situations. :P
There're two sets of computations that TweakScale needs to carry on before loading a savegame for the first time after booting KSP:
- Compute all the scalable part's Dry Cost
- Apply the Sanity Checks
And to save time, they are applied at the same time for each part.
Problem: I can execute these steps only after all PartModules are fully initialised on the prefab. This means that I can't safely apply them on the Loading Scene, when all the PartModules are "Load" with a null on the configNode (meaning this is a prefab initialisation, not a game loading), as I can't say if TweakScale is the last (or not!) PartModule being initialised on the damned part.
The solution that I choose is do on a CoRoutine (exactly due MH) these computations the first time the Main Menu is shown. This had worked (almost) flawlessly, besides Making History kinda screwing up my life because it creates parts on the GameDatabase also on the first time the Main Menu is shown. TweakScale had borked shamelessly the first time I tried it with Making History due this and the solution I took was to monitor the size of the GameDatabase "folder" related to Parts and postpone the computation until it stops changing plus some tens of frames for good measure (I think it was one of the first problems I tackled down on TS, still on the 2.4.0.x experimental times).
It works (most of the time).
Problem: when we overload KSP too much, Unity starts to drop frames in a (desperate) attempt to keep the game useable - and where I shoved the code that does all that computations? Yeah, on a Co-Routine. In an attempt to avoid stuttering the Main Menu, the previous Authors (and now me on the Sanity Checks) choose to split the computations across the frames.
This works pretty well on beefier rigs - the higher the FPS, the faster TweakScale will do the job and call it a day.
But on heavily overloaded machines things go down trough the tubes: with frames being dropped, that computations I mentioned get delayed, and more delayed, and no rarely two things happen (usually concomitantly!!):
Making History gets delayed too, and TweakScale ends checking for the flag condition (the size of the GameDatabase) too soon and, assuming it can starts its work, it starts to work and then MH kicks in and we have again the problem I had with MH in 2018 when I started my tenure on TS
So many frames are dropped that sometimes TweakScale checks a part per second (or less!!!) and so the user fatally starts a new game before TweakScale completes the computations!!!
The item 1 is a pain in the SAS, because without the Sanity Checks a lot of bad situations beyound TS control are not detected, and let pass trough into the loading savegame.But the item 2 is pretty nasty, because a lot of parts ends up being upgrade pipelined into the savegame without the dry cost, i.e., with a DryCost of zero.
And I'm pretty sure by now that this was the reason of some complains in the past that I never managed to reproduce… It took a fellow Kerbonaut with an unrelated problem and a huge patience and good will to endure almost 10 days of exploratory testings on his rig until I could reproduce the problem in a way I could identify the cause!
Thinking on it, I concluded that my problem is trying to "play too nice", trying to prevent hindering the Main Menu animation. Currently I'm working on refactoring the whole DryCost + SanityChecks stunt on a single frame and then just take the hit of doing everything on a single frame (surely causing a hiccup on the Main Menu - at least, it happens only once).
(Recall have the very same problem, by the way…)
Source: Forum.
Implemented on commit #256
The damned thing works, apparently, but I will keep this open until I have time to fully retest the Warning Dialogs.
There's one caveat, however, that I need to document somewhere and this is the right place to do so.
Making History, effectively, creates new parts into the GameDatabase at Main Menu - what I think it's a mistake. Historically, everything is already loaded and set at Main Menu, MH introduced a critical behaviour change on a historically stablished M.O..
That stunt I coded at that time was made because I was trying to stick with the historical behaviour - not to mention the mindset of criticising every available part on the game. Now, whatever Making History is creating at Main Menu, is going ahead unchecked.