win32: support get display fps

This commit is contained in:
Avi Halachmi (:avih) 2015-03-10 20:25:30 +02:00 committed by wm4
parent 6de3fe0b34
commit f881a520fd
1 changed files with 54 additions and 0 deletions

View File

@ -105,6 +105,9 @@ struct vo_w32_state {
int high_surrogate;
ITaskbarList2 *taskbar_list;
// updates on move/resize/displaychange
double display_fps;
};
typedef struct tagDropTarget {
@ -563,6 +566,48 @@ static void wakeup_gui_thread(void *ctx)
PostMessage(w32->window, WM_USER, 0, 0);
}
static double vo_w32_get_display_fps(void)
{
DEVMODE dm;
dm.dmSize = sizeof(DEVMODE);
dm.dmDriverExtra = 0;
if (!EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dm))
return -1;
// May return 0 or 1 which "represent the display hardware's default refresh rate"
// https://msdn.microsoft.com/en-us/library/windows/desktop/dd183565%28v=vs.85%29.aspx
// mpv validates this value with a threshold of 1, so don't return exactly 1
if (dm.dmDisplayFrequency == 1)
return 0;
// dm.dmDisplayFrequency is an integer which is rounded down, so it's
// highly likely that 23 represents 24/1.001, 59 represents 60/1.001, etc.
// A caller can always reproduce the original value by using floor.
double rv = dm.dmDisplayFrequency;
switch (dm.dmDisplayFrequency) {
case 23:
case 29:
case 59:
case 71:
case 119:
rv = (rv + 1) / 1.001;
}
return rv;
}
static void update_display_fps(void *ctx)
{
struct vo_w32_state *w32 = ctx;
double fps = vo_w32_get_display_fps();
if (fps != w32->display_fps) {
w32->display_fps = fps;
signal_events(w32, VO_EVENT_WIN_STATE);
MP_VERBOSE(w32, "display-fps: %f\n", fps);
}
}
static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam,
LPARAM lParam)
{
@ -588,6 +633,7 @@ static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam,
ClientToScreen(w32->window, &p);
w32->window_x = p.x;
w32->window_y = p.y;
update_display_fps(w32); // if we moved between monitors
MP_VERBOSE(w32, "move window: %d:%d\n", w32->window_x, w32->window_y);
break;
}
@ -596,6 +642,7 @@ static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam,
if (GetClientRect(w32->window, &r) && r.right > 0 && r.bottom > 0) {
w32->dw = r.right;
w32->dh = r.bottom;
update_display_fps(w32); // if we moved between monitors
signal_events(w32, VO_EVENT_RESIZE);
MP_VERBOSE(w32, "resize window: %d:%d\n", w32->dw, w32->dh);
}
@ -745,6 +792,9 @@ static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam,
mouse_button = HIWORD(wParam) == 1 ? MP_MOUSE_BTN5 : MP_MOUSE_BTN6;
mouse_button |= MP_KEY_STATE_UP;
break;
case WM_DISPLAYCHANGE:
update_display_fps(w32);
break;
}
if (mouse_button) {
@ -1279,6 +1329,10 @@ static int gui_thread_control(struct vo_w32_state *w32, int request, void *arg)
talloc_free(title);
return VO_TRUE;
}
case VOCTRL_GET_DISPLAY_FPS:
update_display_fps(w32);
*(double*) arg = w32->display_fps;
return VO_TRUE;
}
return VO_NOTIMPL;
}