GTcreyon / SM63Redux

Code base for Super Mario 63 Redux
https://sm63redux.com
Mozilla Public License 2.0
193 stars 25 forks source link

Drastically optimize pause menu elements #300

Open Koopa1018 opened 2 months ago

Koopa1018 commented 2 months ago

Description of changes

On profiling the normal gameplay loop, it was discovered that several pause menu elements had startlingly high performance costs. This PR optimizes them down to reasonable levels.

The bigger offender was the function _get_joypad_buttons in rebind_option.gd, which was profiled as using 11(!) ms of CPU time in each frame. This function returns an array of arrays of button names, indexed by logical button index and by controller brand. On inspection, it was found that this function was called once for every binding of every action, every frame, and doing the same 25 string translations every time (which suggests 25 disk reads). Assuming one binding for every action--which I know is lowballing it--that's 25 * 25 = 625 total translations per frame, literally 98% of which are repeated work.

Optimizing the script thus becomes a matter of reusing work. This can be done:

Some similar string-caching-via-statics work was also done to get_joypad_motion_name. This is mostly for methodological consistency, but if somebody were to make very strange mapping choices ("wassup YouTube, today I'm gonna be playing SM63R using just the left and right analog stick!"), I could see it saving actual performance.

I also chose to optimize level_info.gd. This was much less of a problem script, but it still seemed appropriate to switch it from detecting locale via _process to detecting via engine notification, especially since rebind_option had shown me how to do that. This saves about 0.15ms--not much, but still seemed excessive for a static menu element.

Some mild refactors have also been sprinkled in, including obligatory reordering functions to standard and commenting everything I touch.