High Hz Synchronization (#15798)
* High Hz Synchronization Makes adjustment to driver_adjust_system_rates and related functions to handle Hz skew adjustment for high refresh rates better, especially when using effective refresh modifiers like swap interval or BFI. * Reorder for Build Fix Reorder declaration for build fix
This commit is contained in:
parent
777d96d20a
commit
ce6a00b495
|
@ -13346,6 +13346,8 @@ static bool setting_append_list(
|
||||||
general_read_handler);
|
general_read_handler);
|
||||||
(*list)[list_info->index - 1].action_ok = &setting_action_ok_uint;
|
(*list)[list_info->index - 1].action_ok = &setting_action_ok_uint;
|
||||||
menu_settings_list_current_add_range(list, list_info, 0, 5, 1, true, true);
|
menu_settings_list_current_add_range(list, list_info, 0, 5, 1, true, true);
|
||||||
|
MENU_SETTINGS_LIST_CURRENT_ADD_CMD(list, list_info, CMD_EVENT_REINIT);
|
||||||
|
SETTINGS_DATA_LIST_CURRENT_ADD_FLAGS(list, list_info, SD_FLAG_CMD_APPLY_AUTO);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
47
retroarch.c
47
retroarch.c
|
@ -601,12 +601,24 @@ static float audio_driver_monitor_adjust_system_rates(
|
||||||
double input_fps,
|
double input_fps,
|
||||||
float video_refresh_rate,
|
float video_refresh_rate,
|
||||||
unsigned video_swap_interval,
|
unsigned video_swap_interval,
|
||||||
|
unsigned black_frame_insertion,
|
||||||
float audio_max_timing_skew)
|
float audio_max_timing_skew)
|
||||||
{
|
{
|
||||||
float inp_sample_rate = input_sample_rate;
|
float inp_sample_rate = input_sample_rate;
|
||||||
float target_video_sync_rate = video_refresh_rate
|
|
||||||
/ (float)video_swap_interval;
|
/* This much like the auto swap interval algorithm and will
|
||||||
float timing_skew =
|
* find the correct desired target rate the majority of sane
|
||||||
|
* cases. Any failures should be no worse than the previous
|
||||||
|
* very incomplete high hz skew adjustments. */
|
||||||
|
float refresh_ratio = video_refresh_rate/input_fps;
|
||||||
|
unsigned refresh_closest_multiple = (unsigned)(refresh_ratio + 0.5f);
|
||||||
|
float target_video_sync_rate = video_refresh_rate;
|
||||||
|
float timing_skew = 0.0f;
|
||||||
|
|
||||||
|
if (refresh_closest_multiple > 1)
|
||||||
|
target_video_sync_rate /= (((float)black_frame_insertion + 1.0f) * (float)video_swap_interval);
|
||||||
|
|
||||||
|
timing_skew =
|
||||||
fabs(1.0f - input_fps / target_video_sync_rate);
|
fabs(1.0f - input_fps / target_video_sync_rate);
|
||||||
if (timing_skew <= audio_max_timing_skew)
|
if (timing_skew <= audio_max_timing_skew)
|
||||||
return (inp_sample_rate * target_video_sync_rate / input_fps);
|
return (inp_sample_rate * target_video_sync_rate / input_fps);
|
||||||
|
@ -620,18 +632,23 @@ static bool video_driver_monitor_adjust_system_rates(
|
||||||
bool vrr_runloop_enable,
|
bool vrr_runloop_enable,
|
||||||
float audio_max_timing_skew,
|
float audio_max_timing_skew,
|
||||||
unsigned video_swap_interval,
|
unsigned video_swap_interval,
|
||||||
|
unsigned black_frame_insertion,
|
||||||
double input_fps)
|
double input_fps)
|
||||||
{
|
{
|
||||||
float target_video_sync_rate = timing_skew_hz;
|
float target_video_sync_rate = timing_skew_hz;
|
||||||
|
|
||||||
/* Divide target rate only when using Auto interval */
|
/* Same concept as for audio driver adjust. */
|
||||||
if (_video_swap_interval == 0)
|
float refresh_ratio = target_video_sync_rate/input_fps;
|
||||||
target_video_sync_rate /= (float)video_swap_interval;
|
unsigned refresh_closest_multiple = (unsigned)(refresh_ratio + 0.5f);
|
||||||
|
float timing_skew = 0.0f;
|
||||||
|
|
||||||
|
if (refresh_closest_multiple > 1)
|
||||||
|
target_video_sync_rate /= (((float)black_frame_insertion + 1.0f) * (float)video_swap_interval);
|
||||||
|
|
||||||
if (!vrr_runloop_enable)
|
if (!vrr_runloop_enable)
|
||||||
{
|
{
|
||||||
float timing_skew = fabs(
|
timing_skew =
|
||||||
1.0f - input_fps / target_video_sync_rate);
|
fabs(1.0f - input_fps / target_video_sync_rate);
|
||||||
/* We don't want to adjust pitch too much. If we have extreme cases,
|
/* We don't want to adjust pitch too much. If we have extreme cases,
|
||||||
* just don't readjust at all. */
|
* just don't readjust at all. */
|
||||||
if (timing_skew <= audio_max_timing_skew)
|
if (timing_skew <= audio_max_timing_skew)
|
||||||
|
@ -652,7 +669,8 @@ static void driver_adjust_system_rates(
|
||||||
float video_refresh_rate,
|
float video_refresh_rate,
|
||||||
float audio_max_timing_skew,
|
float audio_max_timing_skew,
|
||||||
bool video_adaptive_vsync,
|
bool video_adaptive_vsync,
|
||||||
unsigned video_swap_interval)
|
unsigned video_swap_interval,
|
||||||
|
unsigned black_frame_insertion)
|
||||||
{
|
{
|
||||||
struct retro_system_av_info *av_info = &video_st->av_info;
|
struct retro_system_av_info *av_info = &video_st->av_info;
|
||||||
const struct retro_system_timing *info =
|
const struct retro_system_timing *info =
|
||||||
|
@ -666,6 +684,7 @@ static void driver_adjust_system_rates(
|
||||||
vrr_runloop_enable,
|
vrr_runloop_enable,
|
||||||
(video_st->flags & VIDEO_FLAG_CRT_SWITCHING_ACTIVE) ? true : false,
|
(video_st->flags & VIDEO_FLAG_CRT_SWITCHING_ACTIVE) ? true : false,
|
||||||
video_swap_interval,
|
video_swap_interval,
|
||||||
|
black_frame_insertion,
|
||||||
audio_max_timing_skew,
|
audio_max_timing_skew,
|
||||||
video_refresh_rate,
|
video_refresh_rate,
|
||||||
input_fps);
|
input_fps);
|
||||||
|
@ -684,6 +703,7 @@ static void driver_adjust_system_rates(
|
||||||
input_fps,
|
input_fps,
|
||||||
video_refresh_rate,
|
video_refresh_rate,
|
||||||
video_swap_interval,
|
video_swap_interval,
|
||||||
|
black_frame_insertion,
|
||||||
audio_max_timing_skew);
|
audio_max_timing_skew);
|
||||||
|
|
||||||
RARCH_LOG("[Audio]: Set audio input rate to: %.2f Hz.\n",
|
RARCH_LOG("[Audio]: Set audio input rate to: %.2f Hz.\n",
|
||||||
|
@ -707,6 +727,7 @@ static void driver_adjust_system_rates(
|
||||||
vrr_runloop_enable,
|
vrr_runloop_enable,
|
||||||
audio_max_timing_skew,
|
audio_max_timing_skew,
|
||||||
video_swap_interval,
|
video_swap_interval,
|
||||||
|
black_frame_insertion,
|
||||||
input_fps))
|
input_fps))
|
||||||
{
|
{
|
||||||
/* We won't be able to do VSync reliably
|
/* We won't be able to do VSync reliably
|
||||||
|
@ -826,7 +847,8 @@ void drivers_init(
|
||||||
settings->floats.video_refresh_rate,
|
settings->floats.video_refresh_rate,
|
||||||
settings->floats.audio_max_timing_skew,
|
settings->floats.audio_max_timing_skew,
|
||||||
settings->bools.video_adaptive_vsync,
|
settings->bools.video_adaptive_vsync,
|
||||||
settings->uints.video_swap_interval
|
settings->uints.video_swap_interval,
|
||||||
|
settings->uints.video_black_frame_insertion
|
||||||
);
|
);
|
||||||
|
|
||||||
/* Initialize video driver */
|
/* Initialize video driver */
|
||||||
|
@ -1260,6 +1282,8 @@ bool driver_ctl(enum driver_ctl_state state, void *data)
|
||||||
float audio_max_timing_skew = settings->floats.audio_max_timing_skew;
|
float audio_max_timing_skew = settings->floats.audio_max_timing_skew;
|
||||||
bool video_adaptive_vsync = settings->bools.video_adaptive_vsync;
|
bool video_adaptive_vsync = settings->bools.video_adaptive_vsync;
|
||||||
unsigned video_swap_interval = settings->uints.video_swap_interval;
|
unsigned video_swap_interval = settings->uints.video_swap_interval;
|
||||||
|
unsigned
|
||||||
|
black_frame_insertion = settings->uints.video_black_frame_insertion;
|
||||||
|
|
||||||
video_monitor_set_refresh_rate(*hz);
|
video_monitor_set_refresh_rate(*hz);
|
||||||
|
|
||||||
|
@ -1273,7 +1297,8 @@ bool driver_ctl(enum driver_ctl_state state, void *data)
|
||||||
video_refresh_rate,
|
video_refresh_rate,
|
||||||
audio_max_timing_skew,
|
audio_max_timing_skew,
|
||||||
video_adaptive_vsync,
|
video_adaptive_vsync,
|
||||||
video_swap_interval
|
video_swap_interval,
|
||||||
|
black_frame_insertion
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -4399,6 +4399,7 @@ void runloop_set_video_swap_interval(
|
||||||
bool vrr_runloop_enable,
|
bool vrr_runloop_enable,
|
||||||
bool crt_switching_active,
|
bool crt_switching_active,
|
||||||
unsigned swap_interval_config,
|
unsigned swap_interval_config,
|
||||||
|
unsigned black_frame_insertion,
|
||||||
float audio_max_timing_skew,
|
float audio_max_timing_skew,
|
||||||
float video_refresh_rate,
|
float video_refresh_rate,
|
||||||
double input_fps)
|
double input_fps)
|
||||||
|
@ -4425,11 +4426,13 @@ void runloop_set_video_swap_interval(
|
||||||
* > If core fps is higher than display refresh rate,
|
* > If core fps is higher than display refresh rate,
|
||||||
* set swap interval to 1
|
* set swap interval to 1
|
||||||
* > If core fps or display refresh rate are zero,
|
* > If core fps or display refresh rate are zero,
|
||||||
* set swap interval to 1 */
|
* set swap interval to 1
|
||||||
|
* > If BFI is active set swap interval to 1 */
|
||||||
if ( (vrr_runloop_enable)
|
if ( (vrr_runloop_enable)
|
||||||
|| (core_hz > timing_hz)
|
|| (core_hz > timing_hz)
|
||||||
|| (core_hz <= 0.0f)
|
|| (core_hz <= 0.0f)
|
||||||
|| (timing_hz <= 0.0f))
|
|| (timing_hz <= 0.0f)
|
||||||
|
|| (black_frame_insertion))
|
||||||
{
|
{
|
||||||
runloop_st->video_swap_interval_auto = 1;
|
runloop_st->video_swap_interval_auto = 1;
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -396,6 +396,7 @@ void runloop_set_video_swap_interval(
|
||||||
bool vrr_runloop_enable,
|
bool vrr_runloop_enable,
|
||||||
bool crt_switching_active,
|
bool crt_switching_active,
|
||||||
unsigned swap_interval_config,
|
unsigned swap_interval_config,
|
||||||
|
unsigned black_frame_insertion,
|
||||||
float audio_max_timing_skew,
|
float audio_max_timing_skew,
|
||||||
float video_refresh_rate,
|
float video_refresh_rate,
|
||||||
double input_fps);
|
double input_fps);
|
||||||
|
|
Loading…
Reference in New Issue