From fdd6de0d12ea17f713ec3e73e7968198339b7b6d Mon Sep 17 00:00:00 2001 From: David Robillard Date: Sat, 21 May 2022 21:28:08 -0400 Subject: Add puglGetScaleFactor() --- src/win.c | 43 ++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 42 insertions(+), 1 deletion(-) (limited to 'src/win.c') diff --git a/src/win.c b/src/win.c index 8f2a26b..5e70b6f 100644 --- a/src/win.c +++ b/src/win.c @@ -35,6 +35,8 @@ #define PUGL_USER_TIMER_MIN 9470 typedef BOOL(WINAPI* PFN_SetProcessDPIAware)(void); +typedef HRESULT(WINAPI* PFN_GetProcessDpiAwareness)(HANDLE, DWORD*); +typedef HRESULT(WINAPI* PFN_GetScaleFactorForMonitor)(HMONITOR, DWORD*); LRESULT CALLBACK wndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); @@ -112,6 +114,35 @@ puglWinGetWindowExFlags(const PuglView* const view) return WS_EX_NOINHERITLAYOUT | (view->parent ? 0u : WS_EX_APPWINDOW); } +static double +puglWinGetViewScaleFactor(const PuglView* const view) +{ + const HMODULE shcore = LoadLibrary("Shcore.dll"); + if (!shcore) { + return 1.0; + } + + const PFN_GetProcessDpiAwareness GetProcessDpiAwareness = + (PFN_GetProcessDpiAwareness)GetProcAddress(shcore, + "GetProcessDpiAwareness"); + + const PFN_GetScaleFactorForMonitor GetScaleFactorForMonitor = + (PFN_GetScaleFactorForMonitor)GetProcAddress(shcore, + "GetScaleFactorForMonitor"); + + DWORD dpiAware = 0; + DWORD scaleFactor = 100; + if (GetProcessDpiAwareness && GetScaleFactorForMonitor && + !GetProcessDpiAwareness(NULL, &dpiAware) && dpiAware) { + GetScaleFactorForMonitor( + MonitorFromWindow(view->impl->hwnd, MONITOR_DEFAULTTOPRIMARY), + &scaleFactor); + } + + FreeLibrary(shcore); + return (double)scaleFactor / 100.0; +} + PuglWorldInternals* puglInitWorldInternals(PuglWorldType type, PuglWorldFlags PUGL_UNUSED(flags)) { @@ -214,7 +245,8 @@ puglRealize(PuglView* view) puglSetWindowTitle(view, view->title); } - view->impl->cursor = LoadCursor(NULL, IDC_ARROW); + view->impl->scaleFactor = puglWinGetViewScaleFactor(view); + view->impl->cursor = LoadCursor(NULL, IDC_ARROW); puglSetFrame(view, view->frame); SetWindowLongPtr(impl->hwnd, GWLP_USERDATA, (LONG_PTR)view); @@ -604,6 +636,9 @@ handleMessage(PuglView* view, UINT message, WPARAM wParam, LPARAM lParam) InvalidateRect(view->impl->hwnd, NULL, false); } break; + case WM_DISPLAYCHANGE: + view->impl->scaleFactor = puglWinGetViewScaleFactor(view); + break; case WM_WINDOWPOSCHANGED: handleConfigure(view, &event); break; @@ -1002,6 +1037,12 @@ adjustedWindowRect(PuglView* const view, return rect; } +double +puglGetScaleFactor(const PuglView* const view) +{ + return view->impl->scaleFactor; +} + PuglStatus puglSetFrame(PuglView* view, const PuglRect frame) { -- cgit v1.2.1