1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
|
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
// Exit macros
#define DpiuExitOnLastError(x, s, ...) ExitOnLastErrorSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitOnLastErrorDebugTrace(x, s, ...) ExitOnLastErrorDebugTraceSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitWithLastError(x, s, ...) ExitWithLastErrorSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitOnFailure(x, s, ...) ExitOnFailureSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitOnRootFailure(x, s, ...) ExitOnRootFailureSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitOnFailureDebugTrace(x, s, ...) ExitOnFailureDebugTraceSource(DUTIL_SOURCE_DPIUTIL, x, s, __VA_ARGS__)
#define DpiuExitOnNull(p, x, e, s, ...) ExitOnNullSource(DUTIL_SOURCE_DPIUTIL, p, x, e, s, __VA_ARGS__)
#define DpiuExitOnNullWithLastError(p, x, s, ...) ExitOnNullWithLastErrorSource(DUTIL_SOURCE_DPIUTIL, p, x, s, __VA_ARGS__)
#define DpiuExitOnNullDebugTrace(p, x, e, s, ...) ExitOnNullDebugTraceSource(DUTIL_SOURCE_DPIUTIL, p, x, e, s, __VA_ARGS__)
#define DpiuExitOnInvalidHandleWithLastError(p, x, s, ...) ExitOnInvalidHandleWithLastErrorSource(DUTIL_SOURCE_DPIUTIL, p, x, s, __VA_ARGS__)
#define DpiuExitOnWin32Error(e, x, s, ...) ExitOnWin32ErrorSource(DUTIL_SOURCE_DPIUTIL, e, x, s, __VA_ARGS__)
static PFN_GETDPIFORMONITOR vpfnGetDpiForMonitor = NULL;
static PFN_GETDPIFORWINDOW vpfnGetDpiForWindow = NULL;
static HMODULE vhShcoreDll = NULL;
static HMODULE vhUser32Dll = NULL;
static BOOL vfDpiuInitialized = FALSE;
DAPI_(void) DpiuInitialize()
{
HRESULT hr = S_OK;
hr = LoadSystemLibrary(L"Shcore.dll", &vhShcoreDll);
if (SUCCEEDED(hr))
{
// Ignore failures.
vpfnGetDpiForMonitor = reinterpret_cast<PFN_GETDPIFORMONITOR>(::GetProcAddress(vhShcoreDll, "GetDpiForMonitor"));
}
hr = LoadSystemLibrary(L"User32.dll", &vhUser32Dll);
if (SUCCEEDED(hr))
{
// Ignore failures.
vpfnGetDpiForWindow = reinterpret_cast<PFN_GETDPIFORWINDOW>(::GetProcAddress(vhUser32Dll, "GetDpiForWindow"));
}
vfDpiuInitialized = TRUE;
}
DAPI_(void) DpiuUninitialize()
{
if (vhShcoreDll)
{
::FreeLibrary(vhShcoreDll);
}
if (vhUser32Dll)
{
::FreeLibrary(vhUser32Dll);
}
vhShcoreDll = NULL;
vhUser32Dll = NULL;
vpfnGetDpiForMonitor = NULL;
vpfnGetDpiForWindow = NULL;
vfDpiuInitialized = FALSE;
}
DAPI_(void) DpiuGetWindowContext(
__in HWND hWnd,
__in DPIU_WINDOW_CONTEXT* pWindowContext
)
{
HRESULT hr = S_OK;
HMONITOR hMonitor = NULL;
UINT dpiX = 0;
UINT dpiY = 0;
HDC hdc = NULL;
pWindowContext->nDpi = USER_DEFAULT_SCREEN_DPI;
if (vpfnGetDpiForWindow)
{
pWindowContext->nDpi = vpfnGetDpiForWindow(hWnd);
ExitFunction();
}
if (vpfnGetDpiForMonitor)
{
hMonitor = ::MonitorFromWindow(hWnd, MONITOR_DEFAULTTONEAREST);
if (hMonitor)
{
hr = vpfnGetDpiForMonitor(hMonitor, MDT_EFFECTIVE_DPI, &dpiX, &dpiY);
if (SUCCEEDED(hr))
{
pWindowContext->nDpi = dpiX;
ExitFunction();
}
}
}
hdc = ::GetDC(hWnd);
if (hdc)
{
pWindowContext->nDpi = ::GetDeviceCaps(hdc, LOGPIXELSX);
}
LExit:
if (hdc)
{
::ReleaseDC(hWnd, hdc);
}
}
DAPI_(int) DpiuScaleValue(
__in int nDefaultDpiValue,
__in UINT nTargetDpi
)
{
return ::MulDiv(nDefaultDpiValue, nTargetDpi, USER_DEFAULT_SCREEN_DPI);
}
|