mirror of
https://github.com/tangerineturtle1/NX2navi.git
synced 2026-11-15 19:19:58 -04:00
Make the engine's second time step follow the display interval too, so held buttons repeat at the right rate.
Besides the per-frame update that the set ostep patches, the graphics system's update (main+0x3b4ea90) divides 60.0 by the engine's nominal rate and stores the result as a global (main+0x4d41fc8): the 60 Hz frames of an update. Its one reader is the buttons' hold-to-repeat timer (main+0x3483680), which adds it to each held button's time and repeats the button once that passes the button's delay and period. Above 60 fps the global stayed 1.0 a rendered frame, so a held button repeated fps / 60 times too often. Two more ostep sites load frames per update from the patch page there, so the two steps are the same number. NX2NAVI_SPEED_PROBE=1 adds the global to the fps line. Checked: the generator's check passes for all 34 main sites against the 1.1.1 module, and the generated C differs from before only in the patched function. Two 60 s runs of an adult save at about 135 fps, uncapped: before, the global step read 1.000 frames while the game's step was 0.42-0.50; after, it read 0.43-0.46, inside the game's step range; frame rate unchanged (132-138 fps in both). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -30,6 +30,14 @@ set freecam NX2NAVI_PATCH_FREECAM 0
|
||||
# (runtime/frame_rate.c). x10 is rewritten before it is read again, and the tst's flags feed only the fcsel.
|
||||
site ostep main 6e6cc0 1e220c21 @page:x10 # fcsel s1, s1, s2, eq -> adrp x10, page
|
||||
site ostep main 6e6cc4 1e201828 bd410148 # fdiv s8, s1, s0 -> ldr s8, [x10, #256]
|
||||
# The engine's second step: the graphics system's update (main+0x3b4ea90) also divides 60.0 by the same nominal rate
|
||||
# (its +0x2c8) and stores the result as a global, main+0x4d41fc8, the 60 Hz frames of the last update. Its reader is the
|
||||
# hold-to-repeat timer of the buttons (main+0x3483680), which adds it to each held button's time and repeats the button
|
||||
# once that passes the button's delay and period in 60 Hz frames; above 60 fps it added 1.0 a rendered frame, so a held
|
||||
# button repeated fps / 60 times too often. The global takes frames per update from the patch page too, so the two steps
|
||||
# never differ. x9 is not read in the function and is free across the call that follows; the store keeps x8.
|
||||
site ostep main 3b4eaf4 5e21d800 @page:x9 # scvtf s0, s0 -> adrp x9, page
|
||||
site ostep main 3b4eaf8 1e201820 bd410120 # fdiv s0, s1, s0 -> ldr s0, [x9, #256]
|
||||
|
||||
# Physics solver steps: the physics system's step setup (main+0x38aeb80, and the same code in main+0x38afc10) gives the
|
||||
# rigid body world its solver step count for the frame, trunc(frames per update * count + 0.001) with the count at
|
||||
|
||||
@@ -556,6 +556,11 @@ static void speed_report(uint64_t now, double step, int interval) {
|
||||
memcpy(last_pos, p, sizeof p);
|
||||
last_pos_ns = now;
|
||||
}
|
||||
float global_step; // Ocarina 1.1.1: the engine's global step (patches-v111.txt, the set ostep's second site)
|
||||
if (probe && ostep_page && read_guest(MOD_MAIN_BASE + 0x4d41fc8, &global_step, 4)) {
|
||||
size_t o = strlen(pos);
|
||||
snprintf(pos + o, sizeof pos - o, "; global step %.3f frames", (double)global_step);
|
||||
}
|
||||
if (os_step_hi > 0) { // Ocarina: the shortest and longest step given in these frames, and the time still owed
|
||||
size_t o = strlen(pos);
|
||||
snprintf(pos + o, sizeof pos - o, "; step %.3f..%.3f frames, %.1f ms owed", os_step_lo * 60, os_step_hi * 60,
|
||||
|
||||
Reference in New Issue
Block a user