mirror of
https://github.com/WinampDesktop/winamp.git
synced 2025-04-27 16:15:41 -04:00
System: Add frame time graph
This commit is contained in:
parent
fa2fd8f84f
commit
19b4f4e921
@ -264,6 +264,7 @@ void Settings::Load(SettingsInterface& si)
|
|||||||
display_show_resolution = si.GetBoolValue("Display", "ShowResolution", false);
|
display_show_resolution = si.GetBoolValue("Display", "ShowResolution", false);
|
||||||
display_show_cpu = si.GetBoolValue("Display", "ShowCPU", false);
|
display_show_cpu = si.GetBoolValue("Display", "ShowCPU", false);
|
||||||
display_show_gpu = si.GetBoolValue("Display", "ShowGPU", false);
|
display_show_gpu = si.GetBoolValue("Display", "ShowGPU", false);
|
||||||
|
display_show_frame_times = si.GetBoolValue("Display", "ShowFrameTimes", false);
|
||||||
display_show_status_indicators = si.GetBoolValue("Display", "ShowStatusIndicators", true);
|
display_show_status_indicators = si.GetBoolValue("Display", "ShowStatusIndicators", true);
|
||||||
display_show_inputs = si.GetBoolValue("Display", "ShowInputs", false);
|
display_show_inputs = si.GetBoolValue("Display", "ShowInputs", false);
|
||||||
display_show_enhancements = si.GetBoolValue("Display", "ShowEnhancements", false);
|
display_show_enhancements = si.GetBoolValue("Display", "ShowEnhancements", false);
|
||||||
@ -478,6 +479,7 @@ void Settings::Save(SettingsInterface& si) const
|
|||||||
si.SetBoolValue("Display", "ShowResolution", display_show_resolution);
|
si.SetBoolValue("Display", "ShowResolution", display_show_resolution);
|
||||||
si.SetBoolValue("Display", "ShowCPU", display_show_cpu);
|
si.SetBoolValue("Display", "ShowCPU", display_show_cpu);
|
||||||
si.SetBoolValue("Display", "ShowGPU", display_show_gpu);
|
si.SetBoolValue("Display", "ShowGPU", display_show_gpu);
|
||||||
|
si.SetBoolValue("Display", "ShowFrameTimes", display_show_frame_times);
|
||||||
si.SetBoolValue("Display", "ShowStatusIndicators", display_show_status_indicators);
|
si.SetBoolValue("Display", "ShowStatusIndicators", display_show_status_indicators);
|
||||||
si.SetBoolValue("Display", "ShowInputs", display_show_inputs);
|
si.SetBoolValue("Display", "ShowInputs", display_show_inputs);
|
||||||
si.SetBoolValue("Display", "ShowEnhancements", display_show_enhancements);
|
si.SetBoolValue("Display", "ShowEnhancements", display_show_enhancements);
|
||||||
|
@ -137,6 +137,7 @@ struct Settings
|
|||||||
bool display_show_resolution = false;
|
bool display_show_resolution = false;
|
||||||
bool display_show_cpu = false;
|
bool display_show_cpu = false;
|
||||||
bool display_show_gpu = false;
|
bool display_show_gpu = false;
|
||||||
|
bool display_show_frame_times = false;
|
||||||
bool display_show_status_indicators = true;
|
bool display_show_status_indicators = true;
|
||||||
bool display_show_inputs = false;
|
bool display_show_inputs = false;
|
||||||
bool display_show_enhancements = false;
|
bool display_show_enhancements = false;
|
||||||
|
@ -155,12 +155,14 @@ static bool s_display_all_frames = true;
|
|||||||
static bool s_syncing_to_host = false;
|
static bool s_syncing_to_host = false;
|
||||||
|
|
||||||
static float s_average_frame_time_accumulator = 0.0f;
|
static float s_average_frame_time_accumulator = 0.0f;
|
||||||
static float s_worst_frame_time_accumulator = 0.0f;
|
static float s_minimum_frame_time_accumulator = 0.0f;
|
||||||
|
static float s_maximum_frame_time_accumulator = 0.0f;
|
||||||
|
|
||||||
static float s_vps = 0.0f;
|
static float s_vps = 0.0f;
|
||||||
static float s_fps = 0.0f;
|
static float s_fps = 0.0f;
|
||||||
static float s_speed = 0.0f;
|
static float s_speed = 0.0f;
|
||||||
static float s_worst_frame_time = 0.0f;
|
static float s_minimum_frame_time = 0.0f;
|
||||||
|
static float s_maximum_frame_time = 0.0f;
|
||||||
static float s_average_frame_time = 0.0f;
|
static float s_average_frame_time = 0.0f;
|
||||||
static float s_cpu_thread_usage = 0.0f;
|
static float s_cpu_thread_usage = 0.0f;
|
||||||
static float s_cpu_thread_time = 0.0f;
|
static float s_cpu_thread_time = 0.0f;
|
||||||
@ -169,6 +171,8 @@ static float s_sw_thread_time = 0.0f;
|
|||||||
static float s_average_gpu_time = 0.0f;
|
static float s_average_gpu_time = 0.0f;
|
||||||
static float s_accumulated_gpu_time = 0.0f;
|
static float s_accumulated_gpu_time = 0.0f;
|
||||||
static float s_gpu_usage = 0.0f;
|
static float s_gpu_usage = 0.0f;
|
||||||
|
static System::FrameTimeHistory s_frame_time_history;
|
||||||
|
static u32 s_frame_time_history_pos = 0;
|
||||||
static u32 s_last_frame_number = 0;
|
static u32 s_last_frame_number = 0;
|
||||||
static u32 s_last_internal_frame_number = 0;
|
static u32 s_last_internal_frame_number = 0;
|
||||||
static u32 s_last_global_tick_counter = 0;
|
static u32 s_last_global_tick_counter = 0;
|
||||||
@ -339,9 +343,13 @@ float System::GetAverageFrameTime()
|
|||||||
{
|
{
|
||||||
return s_average_frame_time;
|
return s_average_frame_time;
|
||||||
}
|
}
|
||||||
float System::GetWorstFrameTime()
|
float System::GetMinimumFrameTime()
|
||||||
{
|
{
|
||||||
return s_worst_frame_time;
|
return s_minimum_frame_time;
|
||||||
|
}
|
||||||
|
float System::GetMaximumFrameTime()
|
||||||
|
{
|
||||||
|
return s_maximum_frame_time;
|
||||||
}
|
}
|
||||||
float System::GetThrottleFrequency()
|
float System::GetThrottleFrequency()
|
||||||
{
|
{
|
||||||
@ -371,6 +379,14 @@ float System::GetGPUAverageTime()
|
|||||||
{
|
{
|
||||||
return s_average_gpu_time;
|
return s_average_gpu_time;
|
||||||
}
|
}
|
||||||
|
const System::FrameTimeHistory& System::GetFrameTimeHistory()
|
||||||
|
{
|
||||||
|
return s_frame_time_history;
|
||||||
|
}
|
||||||
|
u32 System::GetFrameTimeHistoryPos()
|
||||||
|
{
|
||||||
|
return s_frame_time_history_pos;
|
||||||
|
}
|
||||||
|
|
||||||
bool System::IsExeFileName(const std::string_view& path)
|
bool System::IsExeFileName(const std::string_view& path)
|
||||||
{
|
{
|
||||||
@ -802,6 +818,7 @@ void System::SetDefaultSettings(SettingsInterface& si)
|
|||||||
temp.display_show_resolution = g_settings.display_show_resolution;
|
temp.display_show_resolution = g_settings.display_show_resolution;
|
||||||
temp.display_show_cpu = g_settings.display_show_cpu;
|
temp.display_show_cpu = g_settings.display_show_cpu;
|
||||||
temp.display_show_gpu = g_settings.display_show_gpu;
|
temp.display_show_gpu = g_settings.display_show_gpu;
|
||||||
|
temp.display_show_frame_times = g_settings.display_show_frame_times;
|
||||||
|
|
||||||
// keep controller, we reset it elsewhere
|
// keep controller, we reset it elsewhere
|
||||||
for (u32 i = 0; i < NUM_CONTROLLER_AND_CARD_PORTS; i++)
|
for (u32 i = 0; i < NUM_CONTROLLER_AND_CARD_PORTS; i++)
|
||||||
@ -1305,12 +1322,14 @@ bool System::Initialize(bool force_software_renderer)
|
|||||||
s_fast_forward_enabled = false;
|
s_fast_forward_enabled = false;
|
||||||
|
|
||||||
s_average_frame_time_accumulator = 0.0f;
|
s_average_frame_time_accumulator = 0.0f;
|
||||||
s_worst_frame_time_accumulator = 0.0f;
|
s_minimum_frame_time_accumulator = 0.0f;
|
||||||
|
s_maximum_frame_time_accumulator = 0.0f;
|
||||||
|
|
||||||
s_vps = 0.0f;
|
s_vps = 0.0f;
|
||||||
s_fps = 0.0f;
|
s_fps = 0.0f;
|
||||||
s_speed = 0.0f;
|
s_speed = 0.0f;
|
||||||
s_worst_frame_time = 0.0f;
|
s_minimum_frame_time = 0.0f;
|
||||||
|
s_maximum_frame_time = 0.0f;
|
||||||
s_average_frame_time = 0.0f;
|
s_average_frame_time = 0.0f;
|
||||||
s_cpu_thread_usage = 0.0f;
|
s_cpu_thread_usage = 0.0f;
|
||||||
s_cpu_thread_time = 0.0f;
|
s_cpu_thread_time = 0.0f;
|
||||||
@ -1326,6 +1345,8 @@ bool System::Initialize(bool force_software_renderer)
|
|||||||
s_last_cpu_time = 0;
|
s_last_cpu_time = 0;
|
||||||
s_fps_timer.Reset();
|
s_fps_timer.Reset();
|
||||||
s_frame_timer.Reset();
|
s_frame_timer.Reset();
|
||||||
|
s_frame_time_history.fill(0.0f);
|
||||||
|
s_frame_time_history_pos = 0;
|
||||||
|
|
||||||
TimingEvents::Initialize();
|
TimingEvents::Initialize();
|
||||||
|
|
||||||
@ -2092,8 +2113,6 @@ void System::DoRunFrame()
|
|||||||
|
|
||||||
void System::RunFrame()
|
void System::RunFrame()
|
||||||
{
|
{
|
||||||
s_frame_timer.Reset();
|
|
||||||
|
|
||||||
if (s_rewind_load_counter >= 0)
|
if (s_rewind_load_counter >= 0)
|
||||||
{
|
{
|
||||||
DoRewind();
|
DoRewind();
|
||||||
@ -2183,9 +2202,12 @@ void System::RunFrames()
|
|||||||
|
|
||||||
void System::UpdatePerformanceCounters()
|
void System::UpdatePerformanceCounters()
|
||||||
{
|
{
|
||||||
const float frame_time = static_cast<float>(s_frame_timer.GetTimeMilliseconds());
|
const float frame_time = static_cast<float>(s_frame_timer.GetTimeMillisecondsAndReset());
|
||||||
|
s_minimum_frame_time_accumulator = (s_minimum_frame_time_accumulator == 0.0f) ? frame_time : std::min(s_minimum_frame_time_accumulator, frame_time);
|
||||||
s_average_frame_time_accumulator += frame_time;
|
s_average_frame_time_accumulator += frame_time;
|
||||||
s_worst_frame_time_accumulator = std::max(s_worst_frame_time_accumulator, frame_time);
|
s_maximum_frame_time_accumulator = std::max(s_maximum_frame_time_accumulator, frame_time);
|
||||||
|
s_frame_time_history[s_frame_time_history_pos] = frame_time;
|
||||||
|
s_frame_time_history_pos = (s_frame_time_history_pos + 1) % NUM_FRAME_TIME_SAMPLES;
|
||||||
|
|
||||||
// update fps counter
|
// update fps counter
|
||||||
const Common::Timer::Value now_ticks = Common::Timer::GetCurrentValue();
|
const Common::Timer::Value now_ticks = Common::Timer::GetCurrentValue();
|
||||||
@ -2204,10 +2226,10 @@ void System::UpdatePerformanceCounters()
|
|||||||
const double time_divider = 1000.0 * (1.0 / static_cast<double>(Threading::GetThreadTicksPerSecond())) *
|
const double time_divider = 1000.0 * (1.0 / static_cast<double>(Threading::GetThreadTicksPerSecond())) *
|
||||||
(1.0 / static_cast<double>(frames_run));
|
(1.0 / static_cast<double>(frames_run));
|
||||||
|
|
||||||
s_worst_frame_time = s_worst_frame_time_accumulator;
|
s_minimum_frame_time = std::exchange(s_minimum_frame_time_accumulator, 0.0f);
|
||||||
s_worst_frame_time_accumulator = 0.0f;
|
s_average_frame_time = std::exchange(s_average_frame_time_accumulator, 0.0f) / frames_run;
|
||||||
s_average_frame_time = s_average_frame_time_accumulator / frames_run;
|
s_maximum_frame_time = std::exchange(s_maximum_frame_time_accumulator, 0.0f);
|
||||||
s_average_frame_time_accumulator = 0.0f;
|
|
||||||
s_vps = static_cast<float>(frames_run / time);
|
s_vps = static_cast<float>(frames_run / time);
|
||||||
s_last_frame_number = s_frame_number;
|
s_last_frame_number = s_frame_number;
|
||||||
s_fps = static_cast<float>(s_internal_frame_number - s_last_internal_frame_number) / time;
|
s_fps = static_cast<float>(s_internal_frame_number - s_last_internal_frame_number) / time;
|
||||||
@ -2240,8 +2262,8 @@ void System::UpdatePerformanceCounters()
|
|||||||
s_accumulated_gpu_time = 0.0f;
|
s_accumulated_gpu_time = 0.0f;
|
||||||
s_presents_since_last_update = 0;
|
s_presents_since_last_update = 0;
|
||||||
|
|
||||||
Log_VerbosePrintf("FPS: %.2f VPS: %.2f CPU: %.2f GPU: %.2f Average: %.2fms Worst: %.2fms", s_fps, s_vps,
|
Log_VerbosePrintf("FPS: %.2f VPS: %.2f CPU: %.2f GPU: %.2f Average: %.2fms Min: %.2fms Max: %.2f ms", s_fps, s_vps,
|
||||||
s_cpu_thread_usage, s_gpu_usage, s_average_frame_time, s_worst_frame_time);
|
s_cpu_thread_usage, s_gpu_usage, s_average_frame_time, s_minimum_frame_time, s_maximum_frame_time);
|
||||||
|
|
||||||
Host::OnPerformanceCountersUpdated();
|
Host::OnPerformanceCountersUpdated();
|
||||||
}
|
}
|
||||||
@ -2258,7 +2280,9 @@ void System::ResetPerformanceCounters()
|
|||||||
s_last_sw_time = 0;
|
s_last_sw_time = 0;
|
||||||
|
|
||||||
s_average_frame_time_accumulator = 0.0f;
|
s_average_frame_time_accumulator = 0.0f;
|
||||||
s_worst_frame_time_accumulator = 0.0f;
|
s_minimum_frame_time_accumulator = 0.0f;
|
||||||
|
s_maximum_frame_time_accumulator = 0.0f;
|
||||||
|
s_frame_timer.Reset();
|
||||||
s_fps_timer.Reset();
|
s_fps_timer.Reset();
|
||||||
ResetThrottler();
|
ResetThrottler();
|
||||||
}
|
}
|
||||||
@ -3491,8 +3515,6 @@ void System::SetRewinding(bool enabled)
|
|||||||
|
|
||||||
void System::DoRewind()
|
void System::DoRewind()
|
||||||
{
|
{
|
||||||
s_frame_timer.Reset();
|
|
||||||
|
|
||||||
if (s_rewind_load_counter == 0)
|
if (s_rewind_load_counter == 0)
|
||||||
{
|
{
|
||||||
const u32 skip_saves = BoolToUInt32(!s_rewinding_first_save);
|
const u32 skip_saves = BoolToUInt32(!s_rewinding_first_save);
|
||||||
|
@ -176,11 +176,15 @@ const std::string& GetRunningTitle();
|
|||||||
bool IsRunningBIOS();
|
bool IsRunningBIOS();
|
||||||
|
|
||||||
// TODO: Move to PerformanceMetrics
|
// TODO: Move to PerformanceMetrics
|
||||||
|
static constexpr u32 NUM_FRAME_TIME_SAMPLES = 150;
|
||||||
|
using FrameTimeHistory = std::array<float, NUM_FRAME_TIME_SAMPLES>;
|
||||||
|
|
||||||
float GetFPS();
|
float GetFPS();
|
||||||
float GetVPS();
|
float GetVPS();
|
||||||
float GetEmulationSpeed();
|
float GetEmulationSpeed();
|
||||||
float GetAverageFrameTime();
|
float GetAverageFrameTime();
|
||||||
float GetWorstFrameTime();
|
float GetMinimumFrameTime();
|
||||||
|
float GetMaximumFrameTime();
|
||||||
float GetThrottleFrequency();
|
float GetThrottleFrequency();
|
||||||
float GetCPUThreadUsage();
|
float GetCPUThreadUsage();
|
||||||
float GetCPUThreadAverageTime();
|
float GetCPUThreadAverageTime();
|
||||||
@ -188,6 +192,8 @@ float GetSWThreadUsage();
|
|||||||
float GetSWThreadAverageTime();
|
float GetSWThreadAverageTime();
|
||||||
float GetGPUUsage();
|
float GetGPUUsage();
|
||||||
float GetGPUAverageTime();
|
float GetGPUAverageTime();
|
||||||
|
const FrameTimeHistory& GetFrameTimeHistory();
|
||||||
|
u32 GetFrameTimeHistoryPos();
|
||||||
|
|
||||||
/// Loads global settings (i.e. EmuConfig).
|
/// Loads global settings (i.e. EmuConfig).
|
||||||
void LoadSettings(bool display_osd_messages);
|
void LoadSettings(bool display_osd_messages);
|
||||||
|
@ -226,6 +226,8 @@ void AdvancedSettingsWidget::addTweakOptions()
|
|||||||
"DisableAllEnhancements", false);
|
"DisableAllEnhancements", false);
|
||||||
addBooleanTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Show Status Indicators"), "Display",
|
addBooleanTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Show Status Indicators"), "Display",
|
||||||
"ShowStatusIndicators", true);
|
"ShowStatusIndicators", true);
|
||||||
|
addBooleanTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Show Frame Times"), "Display",
|
||||||
|
"ShowFrameTimes", false);
|
||||||
addBooleanTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Apply Compatibility Settings"), "Main",
|
addBooleanTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Apply Compatibility Settings"), "Main",
|
||||||
"ApplyCompatibilitySettings", true);
|
"ApplyCompatibilitySettings", true);
|
||||||
addIntRangeTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Display FPS Limit"), "Display", "MaxFPS", 0, 1000, 0);
|
addIntRangeTweakOption(m_dialog, m_ui.tweakOptionTable, tr("Display FPS Limit"), "Display", "MaxFPS", 0, 1000, 0);
|
||||||
@ -303,6 +305,7 @@ void AdvancedSettingsWidget::onResetToDefaultClicked()
|
|||||||
|
|
||||||
setBooleanTweakOption(m_ui.tweakOptionTable, i++, false); // Disable all enhancements
|
setBooleanTweakOption(m_ui.tweakOptionTable, i++, false); // Disable all enhancements
|
||||||
setBooleanTweakOption(m_ui.tweakOptionTable, i++, true); // Show status indicators
|
setBooleanTweakOption(m_ui.tweakOptionTable, i++, true); // Show status indicators
|
||||||
|
setBooleanTweakOption(m_ui.tweakOptionTable, i++, false); // Show frame times
|
||||||
setBooleanTweakOption(m_ui.tweakOptionTable, i++, true); // Apply compatibility settings
|
setBooleanTweakOption(m_ui.tweakOptionTable, i++, true); // Apply compatibility settings
|
||||||
setIntRangeTweakOption(m_ui.tweakOptionTable, i++, 0); // Display FPS limit
|
setIntRangeTweakOption(m_ui.tweakOptionTable, i++, 0); // Display FPS limit
|
||||||
setChoiceTweakOption(m_ui.tweakOptionTable, i++, 0); // Multisample antialiasing
|
setChoiceTweakOption(m_ui.tweakOptionTable, i++, 0); // Multisample antialiasing
|
||||||
|
@ -2661,6 +2661,9 @@ void FullscreenUI::DrawInterfaceSettingsPage()
|
|||||||
"ShowCPU", false);
|
"ShowCPU", false);
|
||||||
DrawToggleSetting(bsi, ICON_FA_SPINNER " Show GPU Usage",
|
DrawToggleSetting(bsi, ICON_FA_SPINNER " Show GPU Usage",
|
||||||
"Shows the host's GPU usage in the top-right corner of the display.", "Display", "ShowGPU", false);
|
"Shows the host's GPU usage in the top-right corner of the display.", "Display", "ShowGPU", false);
|
||||||
|
DrawToggleSetting(bsi, ICON_FA_RULER_HORIZONTAL " Show Frame Times",
|
||||||
|
"Shows a visual history of frame times in the upper-left corner of the display.", "EmuCore/GS",
|
||||||
|
"ShowFrameTimes", false);
|
||||||
DrawToggleSetting(bsi, ICON_FA_RULER_VERTICAL " Show Resolution",
|
DrawToggleSetting(bsi, ICON_FA_RULER_VERTICAL " Show Resolution",
|
||||||
"Shows the current rendering resolution of the system in the top-right corner of the display.",
|
"Shows the current rendering resolution of the system in the top-right corner of the display.",
|
||||||
"Display", "ShowResolution", false);
|
"Display", "ShowResolution", false);
|
||||||
|
@ -472,7 +472,7 @@ bool ImGuiManager::AddIconFonts(float size)
|
|||||||
0xf15d, 0xf15d, 0xf188, 0xf188, 0xf191, 0xf192, 0xf1dd, 0xf1de, 0xf1e6, 0xf1e6, 0xf1eb, 0xf1eb, 0xf1f8, 0xf1f8,
|
0xf15d, 0xf15d, 0xf188, 0xf188, 0xf191, 0xf192, 0xf1dd, 0xf1de, 0xf1e6, 0xf1e6, 0xf1eb, 0xf1eb, 0xf1f8, 0xf1f8,
|
||||||
0xf1fc, 0xf1fc, 0xf242, 0xf242, 0xf245, 0xf245, 0xf26c, 0xf26c, 0xf279, 0xf279, 0xf2d0, 0xf2d0, 0xf2db, 0xf2db,
|
0xf1fc, 0xf1fc, 0xf242, 0xf242, 0xf245, 0xf245, 0xf26c, 0xf26c, 0xf279, 0xf279, 0xf2d0, 0xf2d0, 0xf2db, 0xf2db,
|
||||||
0xf2f2, 0xf2f2, 0xf2f5, 0xf2f5, 0xf3c1, 0xf3c1, 0xf410, 0xf410, 0xf466, 0xf466, 0xf500, 0xf500, 0xf51f, 0xf51f,
|
0xf2f2, 0xf2f2, 0xf2f5, 0xf2f5, 0xf3c1, 0xf3c1, 0xf410, 0xf410, 0xf466, 0xf466, 0xf500, 0xf500, 0xf51f, 0xf51f,
|
||||||
0xf545, 0xf545, 0xf548, 0xf548, 0xf552, 0xf552, 0xf57a, 0xf57a, 0xf5a2, 0xf5a2, 0xf5aa, 0xf5aa, 0xf5e7, 0xf5e7,
|
0xf545, 0xf545, 0xf547, 0xf548, 0xf552, 0xf552, 0xf57a, 0xf57a, 0xf5a2, 0xf5a2, 0xf5aa, 0xf5aa, 0xf5e7, 0xf5e7,
|
||||||
0xf65d, 0xf65e, 0xf6a9, 0xf6a9, 0xf7c2, 0xf7c2, 0xf807, 0xf807, 0xf815, 0xf815, 0xf818, 0xf818, 0xf84c, 0xf84c,
|
0xf65d, 0xf65e, 0xf6a9, 0xf6a9, 0xf7c2, 0xf7c2, 0xf807, 0xf807, 0xf815, 0xf815, 0xf818, 0xf818, 0xf84c, 0xf84c,
|
||||||
0xf8cc, 0xf8cc, 0x0, 0x0};
|
0xf8cc, 0xf8cc, 0x0, 0x0};
|
||||||
|
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
#include "imgui_overlays.h"
|
#include "imgui_overlays.h"
|
||||||
#include "IconsFontAwesome5.h"
|
#include "IconsFontAwesome5.h"
|
||||||
#include "common/assert.h"
|
#include "common/assert.h"
|
||||||
|
#include "common/align.h"
|
||||||
#include "common/file_system.h"
|
#include "common/file_system.h"
|
||||||
#include "common/log.h"
|
#include "common/log.h"
|
||||||
#include "common/string_util.h"
|
#include "common/string_util.h"
|
||||||
@ -27,6 +28,7 @@
|
|||||||
#include "imgui_manager.h"
|
#include "imgui_manager.h"
|
||||||
#include "input_manager.h"
|
#include "input_manager.h"
|
||||||
#include "util/audio_stream.h"
|
#include "util/audio_stream.h"
|
||||||
|
#include "gsl/span"
|
||||||
#include <atomic>
|
#include <atomic>
|
||||||
#include <chrono>
|
#include <chrono>
|
||||||
#include <cmath>
|
#include <cmath>
|
||||||
@ -34,6 +36,16 @@
|
|||||||
#include <mutex>
|
#include <mutex>
|
||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
|
|
||||||
|
#if defined(CPU_X64)
|
||||||
|
#include <emmintrin.h>
|
||||||
|
#elif defined(CPU_AARCH64)
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
#include <arm64_neon.h>
|
||||||
|
#else
|
||||||
|
#include <arm_neon.h>
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
Log_SetChannel(ImGuiManager);
|
Log_SetChannel(ImGuiManager);
|
||||||
|
|
||||||
namespace ImGuiManager {
|
namespace ImGuiManager {
|
||||||
@ -47,6 +59,74 @@ namespace SaveStateSelectorUI {
|
|||||||
static void Draw();
|
static void Draw();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static std::tuple<float, float> GetMinMax(gsl::span<const float> values)
|
||||||
|
{
|
||||||
|
#if defined(CPU_X64)
|
||||||
|
__m128 vmin(_mm_loadu_ps(values.data()));
|
||||||
|
__m128 vmax(vmin);
|
||||||
|
|
||||||
|
const u32 count = static_cast<u32>(values.size());
|
||||||
|
const u32 aligned_count = Common::AlignDownPow2(count, 4);
|
||||||
|
u32 i = 4;
|
||||||
|
for (; i < aligned_count; i += 4)
|
||||||
|
{
|
||||||
|
const __m128 v(_mm_loadu_ps(&values[i]));
|
||||||
|
vmin = _mm_min_ps(v);
|
||||||
|
vmax = _mm_max_ps(v);
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
float min = std::min(vmin.m128_f32[0], std::min(vmin.m128_f32[1], std::min(vmin.m128_f32[2], vmin.m128_f32[3])));
|
||||||
|
float max = std::max(vmax.m128_f32[0], std::max(vmax.m128_f32[1], std::max(vmax.m128_f32[2], vmax.m128_f32[3])));
|
||||||
|
#else
|
||||||
|
float min = std::min(vmin[0], std::min(vmin[1], std::min(vmin[2], vmin[3])));
|
||||||
|
float max = std::max(vmax[0], std::max(vmax[1], std::max(vmax[2], vmax[3])));
|
||||||
|
#endif
|
||||||
|
for (; i < count; i++)
|
||||||
|
{
|
||||||
|
min = std::min(min, values[i]);
|
||||||
|
max = std::max(max, values[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return std::tie(min, max);
|
||||||
|
#elif defined(CPU_AARCH64)
|
||||||
|
float32x4_t vmin(vld1q_f32(values.data()));
|
||||||
|
float32x4_t vmax(vmin);
|
||||||
|
|
||||||
|
const u32 count = static_cast<u32>(values.size());
|
||||||
|
const u32 aligned_count = Common::AlignDownPow2(count, 4);
|
||||||
|
u32 i = 4;
|
||||||
|
for (; i < aligned_count; i += 4)
|
||||||
|
{
|
||||||
|
const float32x4_t v(vld1q_f32(&values[i]));
|
||||||
|
vmin = vminq_f32(v);
|
||||||
|
vmax = vmaxq_f32(v);
|
||||||
|
}
|
||||||
|
|
||||||
|
float min = vminvq_f32(vmin);
|
||||||
|
float max = vmaxvq_f32(vmax);
|
||||||
|
for (; i < count; i++)
|
||||||
|
{
|
||||||
|
min = std::min(min, values[i]);
|
||||||
|
max = std::max(max, values[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return std::tie(min, max);
|
||||||
|
#else
|
||||||
|
float min = values[0];
|
||||||
|
float max = values[0];
|
||||||
|
const u32 count = static_cast<u32>(values.size());
|
||||||
|
for (u32 i = 1; i < count; i++)
|
||||||
|
{
|
||||||
|
min = std::min(min, values[i]);
|
||||||
|
max = std::max(max, values[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return std::tie(min, max);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool s_save_state_selector_ui_open = false;
|
static bool s_save_state_selector_ui_open = false;
|
||||||
|
|
||||||
void ImGuiManager::RenderOverlays()
|
void ImGuiManager::RenderOverlays()
|
||||||
@ -160,7 +240,7 @@ void ImGuiManager::DrawPerformanceOverlay()
|
|||||||
if (g_settings.display_show_cpu)
|
if (g_settings.display_show_cpu)
|
||||||
{
|
{
|
||||||
text.Clear();
|
text.Clear();
|
||||||
text.AppendFmtString("{:.2f}ms ({:.2f}ms worst)", System::GetAverageFrameTime(), System::GetWorstFrameTime());
|
text.AppendFmtString("{:.2f}ms | {:.2f}ms | {:.2f}ms", System::GetMinimumFrameTime(), System::GetMaximumFrameTime(), System::GetAverageFrameTime());
|
||||||
DRAW_LINE(fixed_font, text, IM_COL32(255, 255, 255, 255));
|
DRAW_LINE(fixed_font, text, IM_COL32(255, 255, 255, 255));
|
||||||
|
|
||||||
text.Clear();
|
text.Clear();
|
||||||
@ -241,6 +321,70 @@ void ImGuiManager::DrawPerformanceOverlay()
|
|||||||
DRAW_LINE(standard_font, text, IM_COL32(255, 255, 255, 255));
|
DRAW_LINE(standard_font, text, IM_COL32(255, 255, 255, 255));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (g_settings.display_show_frame_times)
|
||||||
|
{
|
||||||
|
const ImVec2 history_size(200.0f * scale, 50.0f * scale);
|
||||||
|
ImGui::SetNextWindowSize(ImVec2(history_size.x, history_size.y));
|
||||||
|
ImGui::SetNextWindowPos(ImVec2(ImGui::GetIO().DisplaySize.x - margin - history_size.x, position_y));
|
||||||
|
ImGui::PushStyleColor(ImGuiCol_WindowBg, ImVec4(0.0f, 0.0f, 0.0f, 0.25f));
|
||||||
|
ImGui::PushStyleColor(ImGuiCol_FrameBg, ImVec4(0.0f, 0.0f, 0.0f, 0.0f));
|
||||||
|
ImGui::PushStyleColor(ImGuiCol_PlotLines, ImVec4(1.0f, 1.0f, 1.0f, 1.0f));
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f);
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0.0f, 0.0f));
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0f);
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(0.0f, 0.0f));
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_FrameBorderSize, 0.0f);
|
||||||
|
ImGui::PushFont(fixed_font);
|
||||||
|
if (ImGui::Begin("##frame_times", nullptr, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoInputs))
|
||||||
|
{
|
||||||
|
auto [min, max] = GetMinMax(System::GetFrameTimeHistory());
|
||||||
|
|
||||||
|
// add a little bit of space either side, so we're not constantly resizing
|
||||||
|
if ((max - min) < 4.0f)
|
||||||
|
{
|
||||||
|
min = min - std::fmod(min, 1.0f);
|
||||||
|
max = max - std::fmod(max, 1.0f) + 1.0f;
|
||||||
|
min = std::max(min - 2.0f, 0.0f);
|
||||||
|
max += 2.0f;
|
||||||
|
}
|
||||||
|
|
||||||
|
ImGui::PlotEx(
|
||||||
|
ImGuiPlotType_Lines, "##frame_times",
|
||||||
|
[](void*, int idx) -> float {
|
||||||
|
return System::GetFrameTimeHistory()[((System::GetFrameTimeHistoryPos() + idx) %
|
||||||
|
System::NUM_FRAME_TIME_SAMPLES)];
|
||||||
|
},
|
||||||
|
nullptr, System::NUM_FRAME_TIME_SAMPLES, 0, nullptr, min, max, history_size);
|
||||||
|
|
||||||
|
ImDrawList* win_dl = ImGui::GetCurrentWindow()->DrawList;
|
||||||
|
const ImVec2 wpos(ImGui::GetCurrentWindow()->Pos);
|
||||||
|
|
||||||
|
text.Clear();
|
||||||
|
text.AppendFmtString("{:.1f} ms", max);
|
||||||
|
text_size = fixed_font->CalcTextSizeA(fixed_font->FontSize, FLT_MAX, 0.0f, text.GetCharArray(),
|
||||||
|
text.GetCharArray() + text.GetLength());
|
||||||
|
win_dl->AddText(ImVec2(wpos.x + history_size.x - text_size.x - spacing + shadow_offset, wpos.y + shadow_offset),
|
||||||
|
IM_COL32(0, 0, 0, 100), text.GetCharArray(), text.GetCharArray() + text.GetLength());
|
||||||
|
win_dl->AddText(ImVec2(wpos.x + history_size.x - text_size.x - spacing, wpos.y), IM_COL32(255, 255, 255, 255),
|
||||||
|
text.GetCharArray(), text.GetCharArray() + text.GetLength());
|
||||||
|
|
||||||
|
text.Clear();
|
||||||
|
text.AppendFmtString("{:.1f} ms", min);
|
||||||
|
text_size = fixed_font->CalcTextSizeA(fixed_font->FontSize, FLT_MAX, 0.0f, text.GetCharArray(),
|
||||||
|
text.GetCharArray() + text.GetLength());
|
||||||
|
win_dl->AddText(ImVec2(wpos.x + history_size.x - text_size.x - spacing + shadow_offset,
|
||||||
|
wpos.y + history_size.y - fixed_font->FontSize + shadow_offset),
|
||||||
|
IM_COL32(0, 0, 0, 100), text.GetCharArray(), text.GetCharArray() + text.GetLength());
|
||||||
|
win_dl->AddText(
|
||||||
|
ImVec2(wpos.x + history_size.x - text_size.x - spacing, wpos.y + history_size.y - fixed_font->FontSize),
|
||||||
|
IM_COL32(255, 255, 255, 255), text.GetCharArray(), text.GetCharArray() + text.GetLength());
|
||||||
|
}
|
||||||
|
ImGui::End();
|
||||||
|
ImGui::PopFont();
|
||||||
|
ImGui::PopStyleVar(5);
|
||||||
|
ImGui::PopStyleColor(3);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else if (g_settings.display_show_status_indicators && state == System::State::Paused &&
|
else if (g_settings.display_show_status_indicators && state == System::State::Paused &&
|
||||||
!FullscreenUI::HasActiveWindow())
|
!FullscreenUI::HasActiveWindow())
|
||||||
|
Loading…
x
Reference in New Issue
Block a user