From 96af33c434bb210135d73e40b899bd1ee281c601 Mon Sep 17 00:00:00 2001 From: Logan McNaughton <848146+loganmc10@users.noreply.github.com> Date: Sat, 23 Aug 2025 08:54:47 +0200 Subject: [PATCH] Split render frame and update screen, move pause loop (#556) * split render and update screen functions * move pause loop --- build.rs | 1 + parallel-rdp/interface.cpp | 8 ++++++-- parallel-rdp/interface.hpp | 1 + src/device/vi.rs | 12 +++++++++--- src/ui/video.rs | 28 +++++++++++++++++++--------- 5 files changed, 36 insertions(+), 14 deletions(-) diff --git a/build.rs b/build.rs index 599da1b2..78ef6dd3 100644 --- a/build.rs +++ b/build.rs @@ -111,6 +111,7 @@ fn main() { .allowlist_function("rdp_close") .allowlist_function("rdp_set_vi_register") .allowlist_function("rdp_update_screen") + .allowlist_function("rdp_render_frame") .allowlist_function("rdp_process_commands") .allowlist_function("rdp_onscreen_message") .allowlist_function("rdp_check_callback") diff --git a/parallel-rdp/interface.cpp b/parallel-rdp/interface.cpp index a04e12ca..6580b776 100644 --- a/parallel-rdp/interface.cpp +++ b/parallel-rdp/interface.cpp @@ -523,13 +523,17 @@ void rdp_set_vi_register(uint32_t reg, uint32_t value) processor->set_vi_register(RDP::VIRegister(reg), value); } -void rdp_update_screen() +void rdp_render_frame() { auto &device = wsi->get_device(); render_frame(device); + rdp_device.vi_counter += 1; +} + +void rdp_update_screen() +{ wsi->end_frame(); wsi->begin_frame(); - rdp_device.vi_counter += 1; } CALL_BACK rdp_check_callback() diff --git a/parallel-rdp/interface.hpp b/parallel-rdp/interface.hpp index 4e81ec59..ad9421f1 100644 --- a/parallel-rdp/interface.hpp +++ b/parallel-rdp/interface.hpp @@ -42,6 +42,7 @@ extern "C" void rdp_close(); void rdp_set_vi_register(uint32_t reg, uint32_t value); void rdp_update_screen(); + void rdp_render_frame(); CALL_BACK rdp_check_callback(); uint64_t rdp_process_commands(); void rdp_onscreen_message(const char *_message); diff --git a/src/device/vi.rs b/src/device/vi.rs index 568f2c8b..e117c34c 100644 --- a/src/device/vi.rs +++ b/src/device/vi.rs @@ -134,9 +134,9 @@ pub fn write_regs(device: &mut device::Device, address: u64, value: u32, mask: u } pub fn vertical_interrupt_event(device: &mut device::Device) { - ui::video::update_screen(); + ui::video::render_frame(); - let mut speed_limiter_toggled = ui::video::check_callback(device); + let (mut speed_limiter_toggled, paused) = ui::video::check_callback(device); if device.netplay.is_some() { netplay::send_sync_check(device); @@ -146,11 +146,17 @@ pub fn vertical_interrupt_event(device: &mut device::Device) { } } - device.vi.vi_counter += 1; if device.vi.vi_counter.is_multiple_of(device.vi.limit_freq) && device.vi.enable_speed_limiter { speed_limiter(device, speed_limiter_toggled); } + ui::video::update_screen(); + device.vi.vi_counter += 1; + + if device.netplay.is_none() && paused { + ui::video::pause_loop(); + } + if device.cheats.enabled { cheats::execute_cheats(device, device.cheats.cheats.clone()); } diff --git a/src/ui/video.rs b/src/ui/video.rs index 2998c742..0f316aa7 100644 --- a/src/ui/video.rs +++ b/src/ui/video.rs @@ -93,10 +93,13 @@ pub fn close(ui: &ui::Ui) { } pub fn update_screen() { - // when the window is closed, running is set to false unsafe { rdp_update_screen() } } +pub fn render_frame() { + unsafe { rdp_render_frame() } +} + pub fn state_size() -> usize { unsafe { rdp_state_size() } } @@ -130,9 +133,21 @@ pub fn load_state(device: &mut device::Device, rdp_state: *const u8) { } } -pub fn check_callback(device: &mut device::Device) -> bool { +pub fn pause_loop() { + let mut paused = true; + let mut frame_advance = false; + while paused && !frame_advance { + std::thread::sleep(std::time::Duration::from_secs_f64(1.0 / 60.0)); + unsafe { sdl3_sys::events::SDL_PumpEvents() }; + let callback = unsafe { rdp_check_callback() }; + paused = callback.paused; + frame_advance = callback.frame_advance; + } +} + +pub fn check_callback(device: &mut device::Device) -> (bool, bool) { let mut speed_limiter_toggled = false; - let mut callback = unsafe { rdp_check_callback() }; + let callback = unsafe { rdp_check_callback() }; device.cpu.running = callback.emu_running; if device.netplay.is_none() { if callback.save_state { @@ -144,11 +159,6 @@ pub fn check_callback(device: &mut device::Device) -> bool { speed_limiter_toggled = true; device.vi.enable_speed_limiter = callback.enable_speedlimiter; } - while callback.paused && !callback.frame_advance { - std::thread::sleep(std::time::Duration::from_secs_f64(1.0 / 60.0)); - unsafe { sdl3_sys::events::SDL_PumpEvents() }; - callback = unsafe { rdp_check_callback() }; - } } if device.ui.storage.save_state_slot != callback.save_state_slot { @@ -169,7 +179,7 @@ pub fn check_callback(device: &mut device::Device) -> bool { } else if callback.raise_volume { ui::audio::raise_audio_volume(&mut device.ui); } - speed_limiter_toggled + (speed_limiter_toggled, callback.paused) } pub fn set_register(reg: u32, value: u32) {