mirror of
https://github.com/RetroDECK/Duckstation.git
synced 2024-11-25 15:15:40 +00:00
System: Centralize frame presentation
This commit is contained in:
parent
358f87a74d
commit
afaf5ddafd
|
@ -275,7 +275,7 @@ void Host::UpdateDisplayWindow()
|
||||||
|
|
||||||
// If we're paused, re-present the current frame at the new window size.
|
// If we're paused, re-present the current frame at the new window size.
|
||||||
if (System::IsValid() && System::IsPaused())
|
if (System::IsValid() && System::IsPaused())
|
||||||
RenderDisplay(false);
|
System::InvalidateDisplay();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Host::ResizeDisplayWindow(s32 width, s32 height, float scale)
|
void Host::ResizeDisplayWindow(s32 width, s32 height, float scale)
|
||||||
|
@ -292,7 +292,7 @@ void Host::ResizeDisplayWindow(s32 width, s32 height, float scale)
|
||||||
if (System::IsValid())
|
if (System::IsValid())
|
||||||
{
|
{
|
||||||
if (System::IsPaused())
|
if (System::IsPaused())
|
||||||
RenderDisplay(false);
|
System::InvalidateDisplay();
|
||||||
|
|
||||||
System::HostDisplayResized();
|
System::HostDisplayResized();
|
||||||
}
|
}
|
||||||
|
@ -338,50 +338,3 @@ std::unique_ptr<AudioStream> Host::CreateAudioStream(AudioBackend backend, u32 s
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void Host::RenderDisplay(bool skip_present)
|
|
||||||
{
|
|
||||||
Host::BeginPresentFrame();
|
|
||||||
|
|
||||||
// acquire for IO.MousePos.
|
|
||||||
std::atomic_thread_fence(std::memory_order_acquire);
|
|
||||||
|
|
||||||
if (!skip_present)
|
|
||||||
{
|
|
||||||
FullscreenUI::Render();
|
|
||||||
ImGuiManager::RenderTextOverlays();
|
|
||||||
ImGuiManager::RenderOSDMessages();
|
|
||||||
ImGuiManager::RenderSoftwareCursors();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Debug windows are always rendered, otherwise mouse input breaks on skip.
|
|
||||||
ImGuiManager::RenderOverlayWindows();
|
|
||||||
ImGuiManager::RenderDebugWindows();
|
|
||||||
|
|
||||||
bool do_present;
|
|
||||||
if (g_gpu && !skip_present)
|
|
||||||
do_present = g_gpu->PresentDisplay();
|
|
||||||
else
|
|
||||||
do_present = g_gpu_device->BeginPresent(skip_present);
|
|
||||||
|
|
||||||
if (do_present)
|
|
||||||
{
|
|
||||||
g_gpu_device->RenderImGui();
|
|
||||||
g_gpu_device->EndPresent();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// Still need to kick ImGui or it gets cranky.
|
|
||||||
ImGui::Render();
|
|
||||||
}
|
|
||||||
|
|
||||||
ImGuiManager::NewFrame();
|
|
||||||
|
|
||||||
if (g_gpu)
|
|
||||||
g_gpu->RestoreGraphicsAPIState();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Host::InvalidateDisplay()
|
|
||||||
{
|
|
||||||
RenderDisplay(false);
|
|
||||||
}
|
|
||||||
|
|
|
@ -104,10 +104,6 @@ void ReleaseGPUDevice();
|
||||||
/// Called before drawing the OSD and other display elements.
|
/// Called before drawing the OSD and other display elements.
|
||||||
void BeginPresentFrame();
|
void BeginPresentFrame();
|
||||||
|
|
||||||
/// Provided by the host; renders the display.
|
|
||||||
void RenderDisplay(bool skip_present);
|
|
||||||
void InvalidateDisplay();
|
|
||||||
|
|
||||||
namespace Internal {
|
namespace Internal {
|
||||||
/// Retrieves the base settings layer. Must call with lock held.
|
/// Retrieves the base settings layer. Must call with lock held.
|
||||||
SettingsInterface* GetBaseSettingsLayer();
|
SettingsInterface* GetBaseSettingsLayer();
|
||||||
|
|
|
@ -55,7 +55,6 @@ static void HotkeyModifyResolutionScale(s32 increment)
|
||||||
g_gpu->RestoreGraphicsAPIState();
|
g_gpu->RestoreGraphicsAPIState();
|
||||||
g_gpu->UpdateSettings();
|
g_gpu->UpdateSettings();
|
||||||
System::ClearMemorySaveStates();
|
System::ClearMemorySaveStates();
|
||||||
Host::InvalidateDisplay();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -37,6 +37,7 @@
|
||||||
#include "util/audio_stream.h"
|
#include "util/audio_stream.h"
|
||||||
#include "util/cd_image.h"
|
#include "util/cd_image.h"
|
||||||
#include "util/gpu_device.h"
|
#include "util/gpu_device.h"
|
||||||
|
#include "util/imgui_manager.h"
|
||||||
#include "util/ini_settings_interface.h"
|
#include "util/ini_settings_interface.h"
|
||||||
#include "util/input_manager.h"
|
#include "util/input_manager.h"
|
||||||
#include "util/iso_reader.h"
|
#include "util/iso_reader.h"
|
||||||
|
@ -54,6 +55,7 @@
|
||||||
|
|
||||||
#include "fmt/chrono.h"
|
#include "fmt/chrono.h"
|
||||||
#include "fmt/format.h"
|
#include "fmt/format.h"
|
||||||
|
#include "imgui.h"
|
||||||
#include "xxhash.h"
|
#include "xxhash.h"
|
||||||
|
|
||||||
#include <cctype>
|
#include <cctype>
|
||||||
|
@ -1109,6 +1111,7 @@ void System::PauseSystem(bool paused)
|
||||||
PlatformMisc::ResumeScreensaver();
|
PlatformMisc::ResumeScreensaver();
|
||||||
|
|
||||||
Host::OnSystemPaused();
|
Host::OnSystemPaused();
|
||||||
|
InvalidateDisplay();
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1173,7 +1176,7 @@ bool System::LoadState(const char* filename)
|
||||||
|
|
||||||
ResetPerformanceCounters();
|
ResetPerformanceCounters();
|
||||||
ResetThrottler();
|
ResetThrottler();
|
||||||
Host::RenderDisplay(false);
|
InvalidateDisplay();
|
||||||
Log_VerbosePrintf("Loading state took %.2f msec", load_timer.GetTimeMilliseconds());
|
Log_VerbosePrintf("Loading state took %.2f msec", load_timer.GetTimeMilliseconds());
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -1764,6 +1767,15 @@ void System::FrameDone()
|
||||||
if (s_cheat_list)
|
if (s_cheat_list)
|
||||||
s_cheat_list->Apply();
|
s_cheat_list->Apply();
|
||||||
|
|
||||||
|
#ifdef WITH_CHEEVOS
|
||||||
|
if (Achievements::IsActive())
|
||||||
|
Achievements::FrameUpdate();
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef WITH_DISCORD_PRESENCE
|
||||||
|
PollDiscordPresence();
|
||||||
|
#endif
|
||||||
|
|
||||||
if (s_frame_step_request)
|
if (s_frame_step_request)
|
||||||
{
|
{
|
||||||
s_frame_step_request = false;
|
s_frame_step_request = false;
|
||||||
|
@ -1811,27 +1823,10 @@ void System::FrameDone()
|
||||||
SaveRunaheadState();
|
SaveRunaheadState();
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef WITH_CHEEVOS
|
|
||||||
if (Achievements::IsActive())
|
|
||||||
Achievements::FrameUpdate();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef WITH_DISCORD_PRESENCE
|
|
||||||
PollDiscordPresence();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
const Common::Timer::Value current_time = Common::Timer::GetCurrentValue();
|
const Common::Timer::Value current_time = Common::Timer::GetCurrentValue();
|
||||||
if (current_time < s_next_frame_time || s_display_all_frames || s_last_frame_skipped)
|
if (current_time < s_next_frame_time || s_display_all_frames || s_last_frame_skipped)
|
||||||
{
|
{
|
||||||
s_last_frame_skipped = false;
|
s_last_frame_skipped = !PresentDisplay(true);
|
||||||
|
|
||||||
const bool skip_present = g_gpu_device->ShouldSkipDisplayingFrame();
|
|
||||||
Host::RenderDisplay(skip_present);
|
|
||||||
if (!skip_present && g_gpu_device->IsGPUTimingEnabled())
|
|
||||||
{
|
|
||||||
s_accumulated_gpu_time += g_gpu_device->GetAndResetAccumulatedGPUTime();
|
|
||||||
s_presents_since_last_update++;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else if (current_time >= s_next_frame_time)
|
else if (current_time >= s_next_frame_time)
|
||||||
{
|
{
|
||||||
|
@ -1928,6 +1923,8 @@ void System::SingleStepCPU()
|
||||||
g_gpu->FlushRender();
|
g_gpu->FlushRender();
|
||||||
SPU::GeneratePendingSamples();
|
SPU::GeneratePendingSamples();
|
||||||
|
|
||||||
|
InvalidateDisplay();
|
||||||
|
|
||||||
s_system_executing = false;
|
s_system_executing = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1966,7 +1963,7 @@ void System::RecreateSystem()
|
||||||
|
|
||||||
ResetPerformanceCounters();
|
ResetPerformanceCounters();
|
||||||
ResetThrottler();
|
ResetThrottler();
|
||||||
Host::RenderDisplay(false);
|
InvalidateDisplay();
|
||||||
|
|
||||||
if (was_paused)
|
if (was_paused)
|
||||||
PauseSystem(true);
|
PauseSystem(true);
|
||||||
|
@ -3488,7 +3485,7 @@ void System::CheckForSettingsChanges(const Settings& old_settings)
|
||||||
{
|
{
|
||||||
// if debug device/threaded presentation change, we need to recreate the whole display
|
// if debug device/threaded presentation change, we need to recreate the whole display
|
||||||
const bool recreate_device = (g_settings.gpu_use_debug_device != old_settings.gpu_use_debug_device ||
|
const bool recreate_device = (g_settings.gpu_use_debug_device != old_settings.gpu_use_debug_device ||
|
||||||
g_settings.gpu_threaded_presentation != old_settings.gpu_threaded_presentation);
|
g_settings.gpu_threaded_presentation != old_settings.gpu_threaded_presentation);
|
||||||
|
|
||||||
Host::AddFormattedOSDMessage(5.0f, TRANSLATE("OSDMessage", "Switching to %s%s GPU renderer."),
|
Host::AddFormattedOSDMessage(5.0f, TRANSLATE("OSDMessage", "Switching to %s%s GPU renderer."),
|
||||||
Settings::GetRendererName(g_settings.gpu_renderer),
|
Settings::GetRendererName(g_settings.gpu_renderer),
|
||||||
|
@ -3594,7 +3591,7 @@ void System::CheckForSettingsChanges(const Settings& old_settings)
|
||||||
g_settings.runahead_frames != old_settings.runahead_frames)
|
g_settings.runahead_frames != old_settings.runahead_frames)
|
||||||
{
|
{
|
||||||
g_gpu->UpdateSettings();
|
g_gpu->UpdateSettings();
|
||||||
Host::InvalidateDisplay();
|
InvalidateDisplay();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (g_settings.gpu_widescreen_hack != old_settings.gpu_widescreen_hack ||
|
if (g_settings.gpu_widescreen_hack != old_settings.gpu_widescreen_hack ||
|
||||||
|
@ -3909,7 +3906,7 @@ void System::DoRewind()
|
||||||
|
|
||||||
s_next_frame_time += s_frame_period;
|
s_next_frame_time += s_frame_period;
|
||||||
|
|
||||||
Host::RenderDisplay(false);
|
InvalidateDisplay();
|
||||||
Host::PumpMessagesOnCPUThread();
|
Host::PumpMessagesOnCPUThread();
|
||||||
|
|
||||||
Throttle();
|
Throttle();
|
||||||
|
@ -4578,7 +4575,6 @@ void System::ToggleSoftwareRendering()
|
||||||
Host::AddKeyedFormattedOSDMessage("SoftwareRendering", 5.0f, TRANSLATE("OSDMessage", "Switching to %s renderer..."),
|
Host::AddKeyedFormattedOSDMessage("SoftwareRendering", 5.0f, TRANSLATE("OSDMessage", "Switching to %s renderer..."),
|
||||||
Settings::GetRendererDisplayName(new_renderer));
|
Settings::GetRendererDisplayName(new_renderer));
|
||||||
RecreateGPU(new_renderer);
|
RecreateGPU(new_renderer);
|
||||||
Host::InvalidateDisplay();
|
|
||||||
ResetPerformanceCounters();
|
ResetPerformanceCounters();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4644,6 +4640,63 @@ void System::HostDisplayResized()
|
||||||
g_gpu->UpdateResolutionScale();
|
g_gpu->UpdateResolutionScale();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool System::PresentDisplay(bool allow_skip_present)
|
||||||
|
{
|
||||||
|
const bool skip_present = allow_skip_present && g_gpu_device->ShouldSkipDisplayingFrame();
|
||||||
|
|
||||||
|
Host::BeginPresentFrame();
|
||||||
|
|
||||||
|
// acquire for IO.MousePos.
|
||||||
|
std::atomic_thread_fence(std::memory_order_acquire);
|
||||||
|
|
||||||
|
if (!skip_present)
|
||||||
|
{
|
||||||
|
FullscreenUI::Render();
|
||||||
|
ImGuiManager::RenderTextOverlays();
|
||||||
|
ImGuiManager::RenderOSDMessages();
|
||||||
|
ImGuiManager::RenderSoftwareCursors();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Debug windows are always rendered, otherwise mouse input breaks on skip.
|
||||||
|
ImGuiManager::RenderOverlayWindows();
|
||||||
|
ImGuiManager::RenderDebugWindows();
|
||||||
|
|
||||||
|
bool do_present;
|
||||||
|
if (g_gpu && !skip_present)
|
||||||
|
do_present = g_gpu->PresentDisplay();
|
||||||
|
else
|
||||||
|
do_present = g_gpu_device->BeginPresent(skip_present);
|
||||||
|
|
||||||
|
if (do_present)
|
||||||
|
{
|
||||||
|
g_gpu_device->RenderImGui();
|
||||||
|
g_gpu_device->EndPresent();
|
||||||
|
|
||||||
|
if (g_gpu_device->IsGPUTimingEnabled())
|
||||||
|
{
|
||||||
|
s_accumulated_gpu_time += g_gpu_device->GetAndResetAccumulatedGPUTime();
|
||||||
|
s_presents_since_last_update++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Still need to kick ImGui or it gets cranky.
|
||||||
|
ImGui::Render();
|
||||||
|
}
|
||||||
|
|
||||||
|
ImGuiManager::NewFrame();
|
||||||
|
|
||||||
|
if (g_gpu)
|
||||||
|
g_gpu->RestoreGraphicsAPIState();
|
||||||
|
|
||||||
|
return do_present;
|
||||||
|
}
|
||||||
|
|
||||||
|
void System::InvalidateDisplay()
|
||||||
|
{
|
||||||
|
PresentDisplay(false);
|
||||||
|
}
|
||||||
|
|
||||||
void System::SetTimerResolutionIncreased(bool enabled)
|
void System::SetTimerResolutionIncreased(bool enabled)
|
||||||
{
|
{
|
||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
|
|
|
@ -448,6 +448,10 @@ void RequestDisplaySize(float scale = 0.0f);
|
||||||
/// Call when host display size changes, use with "match display" aspect ratio setting.
|
/// Call when host display size changes, use with "match display" aspect ratio setting.
|
||||||
void HostDisplayResized();
|
void HostDisplayResized();
|
||||||
|
|
||||||
|
/// Renders the display.
|
||||||
|
bool PresentDisplay(bool allow_skip_present);
|
||||||
|
void InvalidateDisplay();
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
// Memory Save States (Rewind and Runahead)
|
// Memory Save States (Rewind and Runahead)
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
|
|
|
@ -415,8 +415,6 @@ void EmuThread::applySettings(bool display_osd_messages /* = false */)
|
||||||
}
|
}
|
||||||
|
|
||||||
System::ApplySettings(display_osd_messages);
|
System::ApplySettings(display_osd_messages);
|
||||||
if (!FullscreenUI::IsInitialized() && System::IsPaused())
|
|
||||||
redrawDisplayWindow();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void EmuThread::reloadGameSettings(bool display_osd_messages /* = false */)
|
void EmuThread::reloadGameSettings(bool display_osd_messages /* = false */)
|
||||||
|
@ -428,8 +426,6 @@ void EmuThread::reloadGameSettings(bool display_osd_messages /* = false */)
|
||||||
}
|
}
|
||||||
|
|
||||||
System::ReloadGameSettings(display_osd_messages);
|
System::ReloadGameSettings(display_osd_messages);
|
||||||
if (!FullscreenUI::IsInitialized() && System::IsPaused())
|
|
||||||
redrawDisplayWindow();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void EmuThread::updateEmuFolders()
|
void EmuThread::updateEmuFolders()
|
||||||
|
@ -509,11 +505,7 @@ void EmuThread::bootSystem(std::shared_ptr<SystemBootParameters> params)
|
||||||
|
|
||||||
setInitialState(params->override_fullscreen);
|
setInitialState(params->override_fullscreen);
|
||||||
|
|
||||||
if (!System::BootSystem(std::move(*params)))
|
System::BootSystem(std::move(*params));
|
||||||
return;
|
|
||||||
|
|
||||||
// force a frame to be drawn to repaint the window
|
|
||||||
Host::InvalidateDisplay();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void EmuThread::bootOrLoadState(std::string path)
|
void EmuThread::bootOrLoadState(std::string path)
|
||||||
|
@ -606,7 +598,7 @@ void EmuThread::redrawDisplayWindow()
|
||||||
if (!g_gpu_device || System::IsShutdown())
|
if (!g_gpu_device || System::IsShutdown())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
Host::RenderDisplay(false);
|
System::InvalidateDisplay();
|
||||||
}
|
}
|
||||||
|
|
||||||
void EmuThread::toggleFullscreen()
|
void EmuThread::toggleFullscreen()
|
||||||
|
@ -726,7 +718,6 @@ void Host::OnSystemPaused()
|
||||||
{
|
{
|
||||||
emit g_emu_thread->systemPaused();
|
emit g_emu_thread->systemPaused();
|
||||||
g_emu_thread->startBackgroundControllerPollTimer();
|
g_emu_thread->startBackgroundControllerPollTimer();
|
||||||
Host::InvalidateDisplay();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Host::OnSystemResumed()
|
void Host::OnSystemResumed()
|
||||||
|
@ -1137,7 +1128,6 @@ void EmuThread::singleStepCPU()
|
||||||
return;
|
return;
|
||||||
|
|
||||||
System::SingleStepCPU();
|
System::SingleStepCPU();
|
||||||
Host::InvalidateDisplay();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void EmuThread::dumpRAM(const QString& filename)
|
void EmuThread::dumpRAM(const QString& filename)
|
||||||
|
@ -1342,7 +1332,7 @@ void EmuThread::run()
|
||||||
System::Internal::IdlePollUpdate();
|
System::Internal::IdlePollUpdate();
|
||||||
if (g_gpu_device)
|
if (g_gpu_device)
|
||||||
{
|
{
|
||||||
Host::RenderDisplay(false);
|
System::PresentDisplay(false);
|
||||||
if (!g_gpu_device->IsVsyncEnabled())
|
if (!g_gpu_device->IsVsyncEnabled())
|
||||||
g_gpu_device->ThrottlePresentation();
|
g_gpu_device->ThrottlePresentation();
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue