1 /*
2 * PROJECT: ReactOS API tests
3 * LICENSE: GPL - See COPYING in the top level directory
4 * PURPOSE: Test for SystemParametersInfo function family
5 * PROGRAMMERS: Giannis Adamopoulos
6 */
7
8 #include "precomp.h"
9
10 static HWND hWnd1, hWnd2;
11
12 static BOOL g_bReadyForDisplayChange = FALSE;
13 static HANDLE g_hSemDisplayChange;
14
15 /* FIXME: test for HWND_TOP, etc...*/
get_iwnd(HWND hWnd)16 static int get_iwnd(HWND hWnd)
17 {
18 if(hWnd == hWnd1) return 1;
19 else if(hWnd == hWnd2) return 2;
20 else return 0;
21 }
22
SysParamsTestProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)23 LRESULT CALLBACK SysParamsTestProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
24 {
25 int iwnd = get_iwnd(hWnd);
26
27 if(message > WM_USER || !iwnd || IsDWmMsg(message) || IseKeyMsg(message))
28 return DefWindowProc(hWnd, message, wParam, lParam);
29
30 switch(message)
31 {
32 case WM_GETICON :
33 case WM_SETICON:
34 break;
35 case WM_WINDOWPOSCHANGING:
36 case WM_WINDOWPOSCHANGED:
37 {
38 WINDOWPOS* pwp = (WINDOWPOS*)lParam;
39 ok(wParam==0,"expected wParam=0\n");
40 RECORD_MESSAGE(iwnd, message, SENT, get_iwnd(pwp->hwndInsertAfter), pwp->flags);
41 break;
42 }
43 case WM_DISPLAYCHANGE:
44 if (g_bReadyForDisplayChange)
45 {
46 g_bReadyForDisplayChange = FALSE;
47 ReleaseSemaphore(g_hSemDisplayChange, 1, 0);
48 }
49 break;
50 default:
51 RECORD_MESSAGE(iwnd, message, SENT, 0,0);
52 }
53 return DefWindowProc(hWnd, message, wParam, lParam);
54 }
55
FlushMessages()56 static void FlushMessages()
57 {
58 MSG msg;
59
60 while (PeekMessage( &msg, 0, 0, 0, PM_REMOVE ))
61 {
62 int iwnd = get_iwnd(msg.hwnd);
63 if(!(msg.message > WM_USER || !iwnd || IsDWmMsg(msg.message) || IseKeyMsg(msg.message)))
64 RECORD_MESSAGE(iwnd, msg.message, POST,0,0);
65 DispatchMessageA( &msg );
66 }
67 }
68
69 static MSG_ENTRY NcMetricsChange_chain[]={
70 {2,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
71 {2,WM_GETMINMAXINFO},
72 {2,WM_NCCALCSIZE},
73 {2,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE | SWP_NOCLIENTMOVE | SWP_NOSIZE},
74 {1,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
75 {1,WM_GETMINMAXINFO},
76 {1,WM_NCCALCSIZE},
77 {1,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE | SWP_NOCLIENTMOVE | SWP_NOSIZE},
78 {0,0}};
79
80 static MSG_ENTRY NcMetricsChange1_chain[]={
81 {2,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
82 {2,WM_GETMINMAXINFO},
83 {2,WM_NCCALCSIZE},
84 {2,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE | SWP_NOCLIENTMOVE | SWP_NOSIZE},
85 {1,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
86 {1,WM_GETMINMAXINFO},
87 {1,WM_NCCALCSIZE},
88 {1,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE | SWP_NOCLIENTMOVE | SWP_NOSIZE},
89 {2,WM_SETTINGCHANGE},
90 {1,WM_SETTINGCHANGE},
91 {0,0}};
92
93 static MSG_ENTRY CaptionHeight_chain[]={
94 {2,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
95 {2,WM_GETMINMAXINFO},
96 {2,WM_NCCALCSIZE},
97 {2,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE},
98 {2,WM_MOVE},
99 {1,WM_WINDOWPOSCHANGING, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW},
100 {1,WM_GETMINMAXINFO},
101 {1,WM_NCCALCSIZE},
102 {1,WM_WINDOWPOSCHANGED, SENT, 0, SWP_FRAMECHANGED|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER|SWP_NOREDRAW | SWP_NOCLIENTSIZE},
103 {1,WM_MOVE},
104 {0,0}};
105
Test_NonClientMetrics()106 static void Test_NonClientMetrics()
107 {
108 NONCLIENTMETRICS NonClientMetrics;
109
110 /* WARNING: this test requires themes and dwm to be disabled */
111
112 SetCursorPos(0,0);
113
114 /* Retrieve th non client metrics */
115 NonClientMetrics.cbSize = sizeof(NONCLIENTMETRICS);
116 SystemParametersInfo(SPI_GETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICS), &NonClientMetrics, 0);
117 FlushMessages();
118 COMPARE_CACHE(empty_chain);
119
120 /* Set the non client metric without making any change */
121 SystemParametersInfo(SPI_SETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICS), &NonClientMetrics, 0);
122 FlushMessages();
123 COMPARE_CACHE(NcMetricsChange_chain);
124
125 /* Set the same metrics again with the SPIF_SENDCHANGE param */
126 SystemParametersInfo(SPI_SETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICS), &NonClientMetrics, SPIF_SENDCHANGE|SPIF_UPDATEINIFILE );
127 FlushMessages();
128 COMPARE_CACHE(NcMetricsChange1_chain);
129
130 /* Slightly change the caption height */
131 NonClientMetrics.iCaptionHeight += 1;
132 SystemParametersInfo(SPI_SETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICS), &NonClientMetrics, 0);
133 FlushMessages();
134 COMPARE_CACHE(CaptionHeight_chain);
135
136 /* Restore the original caption height */
137 NonClientMetrics.iCaptionHeight -= 1;
138 SystemParametersInfo(SPI_SETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICS), &NonClientMetrics, 0);
139 FlushMessages();
140 COMPARE_CACHE(CaptionHeight_chain);
141 }
142
Test_MouseSpeed()143 static void Test_MouseSpeed()
144 {
145 ULONG ulMouseSpeed, temp;
146 BOOL ret;
147
148 ret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &ulMouseSpeed, 0);
149 ok(ret, "SystemParametersInfo failed\n");
150 ok(ulMouseSpeed >= 1 && ulMouseSpeed <=20, "Wrong mouse speed (%d)\n", (int)ulMouseSpeed);
151
152 temp = 1;
153 ret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, UlongToPtr(temp), SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
154 ok(ret, "SystemParametersInfo failed\n");
155 ret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &temp, 0);
156 ok(ret, "SystemParametersInfo failed\n");
157 ok(temp == 1, "SPI_GETMOUSESPEED did not get value set by SPI_SETMOUSESPEED (%d instead of 1)\n", (int)temp);
158
159 temp = 20;
160 ret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, UlongToPtr(temp), SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
161 ok(ret, "SystemParametersInfo failed\n");
162 ret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &temp, 0);
163 ok(ret, "SystemParametersInfo failed\n");
164 ok(temp == 20, "SPI_GETMOUSESPEED did not get value set by SPI_SETMOUSESPEED (%d instead of 20)\n", (int)temp);
165
166 temp = 21;
167 ret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, UlongToPtr(temp), SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
168 ok(!ret, "expected SystemParametersInfo to fail\n");
169 ret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &temp, 0);
170 ok(ret, "SystemParametersInfo failed\n");
171 ok(temp == 20, "SPI_GETMOUSESPEED got unexpected value (%d instead of 20)\n", (int)temp);
172
173 temp = 0;
174 ret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, UlongToPtr(temp), SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
175 ok(!ret, "expected SystemParametersInfo to fail\n");
176 ret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &temp, 0);
177 ok(ret, "SystemParametersInfo failed\n");
178 ok(temp == 20, "SPI_GETMOUSESPEED got unexpected value (%d instead of 20)\n", (int)temp);
179
180 ret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, UlongToPtr(ulMouseSpeed), SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
181 ok(ret, "SystemParametersInfo failed\n");
182 }
183
Test_GradientCaptions(void)184 static void Test_GradientCaptions(void)
185 {
186 BOOL ret;
187 LONG lResult;
188 DWORD dwResult;
189 BOOL bGradientCaptions, bModeFound;
190 DEVMODEW OldDevMode, NewDevMode;
191 INT iMode;
192
193 ret = SystemParametersInfo(SPI_GETGRADIENTCAPTIONS, 0, &bGradientCaptions, 0);
194 ok(ret, "SystemParametersInfo failed\n");
195 if (bGradientCaptions == FALSE)
196 {
197 skip("GRADIENTCAPTIONS value has changed from its original state\n");
198 return;
199 }
200
201 /* Try to find a graphics mode with 16 or 256 colors */
202 iMode = 0;
203 bModeFound = FALSE;
204 while (EnumDisplaySettingsW(NULL, iMode, &NewDevMode))
205 {
206 if ((NewDevMode.dmBitsPerPel == 4) ||
207 (NewDevMode.dmBitsPerPel == 8))
208 {
209 bModeFound = TRUE;
210 break;
211 }
212
213 ++iMode;
214 }
215 if (!bModeFound)
216 {
217 skip("4bpp/8bpp graphics mode is not supported\n");
218 return;
219 }
220
221 /* Save the current graphics mode */
222 ret = EnumDisplaySettingsW(NULL, ENUM_CURRENT_SETTINGS, &OldDevMode);
223 ok(ret, "EnumDisplaySettingsW failed\n");
224
225 g_hSemDisplayChange = CreateSemaphoreW(NULL, 0, 1, NULL);
226
227 /* Switch to the new graphics mode */
228 g_bReadyForDisplayChange = TRUE;
229 lResult = ChangeDisplaySettingsExW(NULL, &NewDevMode, NULL, 0, NULL);
230 if (lResult == DISP_CHANGE_SUCCESSFUL)
231 {
232 dwResult = WaitForSingleObject(g_hSemDisplayChange, 10000);
233 ok(dwResult == WAIT_OBJECT_0, "Waiting for the WM_DISPLAYCHANGE message timed out\n");
234 }
235 g_bReadyForDisplayChange = FALSE;
236 ok(lResult == DISP_CHANGE_SUCCESSFUL, "ChangeDisplaySettingsExW returned %ld\n", lResult);
237
238 /* SPI_GETGRADIENTCAPTIONS will now always return FALSE */
239 ret = SystemParametersInfo(SPI_GETGRADIENTCAPTIONS, 0, &bGradientCaptions, 0);
240 ok(ret, "SystemParametersInfo failed\n");
241 ok(bGradientCaptions == FALSE, "SPI_GETGRADIENTCAPTIONS got unexpected value (%d instead of 0)\n", bGradientCaptions);
242
243 /* Enable gradient captions */
244 bGradientCaptions = TRUE;
245 SystemParametersInfo(SPI_SETGRADIENTCAPTIONS, 0, UlongToPtr(bGradientCaptions), 0);
246
247 /* Still FALSE */
248 ret = SystemParametersInfo(SPI_GETGRADIENTCAPTIONS, 0, &bGradientCaptions, 0);
249 ok(ret, "SystemParametersInfo failed\n");
250 ok(bGradientCaptions == FALSE, "SPI_GETGRADIENTCAPTIONS got unexpected value (%d instead of 0)\n", bGradientCaptions);
251
252 /* Restore the previous graphics mode */
253 g_bReadyForDisplayChange = TRUE;
254 lResult = ChangeDisplaySettingsExW(NULL, &OldDevMode, NULL, 0, NULL);
255 if (lResult == DISP_CHANGE_SUCCESSFUL)
256 {
257 dwResult = WaitForSingleObject(g_hSemDisplayChange, 10000);
258 ok(dwResult == WAIT_OBJECT_0, "Waiting for the WM_DISPLAYCHANGE message timed out\n");
259 }
260 g_bReadyForDisplayChange = FALSE;
261 ok(lResult == DISP_CHANGE_SUCCESSFUL, "ChangeDisplaySettingsExW returned %ld\n", lResult);
262
263 /* The original value should be restored */
264 ret = SystemParametersInfo(SPI_GETGRADIENTCAPTIONS, 0, &bGradientCaptions, 0);
265 ok(ret, "SystemParametersInfo failed\n");
266 ok(bGradientCaptions == TRUE, "SPI_GETGRADIENTCAPTIONS got unexpected value (%d instead of 1)\n", bGradientCaptions);
267
268 CloseHandle(g_hSemDisplayChange);
269 }
270
START_TEST(SystemParametersInfo)271 START_TEST(SystemParametersInfo)
272 {
273 RegisterSimpleClass(SysParamsTestProc, L"sysparamstest");
274 hWnd1 = CreateWindowW(L"sysparamstest", L"sysparamstest", WS_OVERLAPPEDWINDOW,
275 20, 20, 300, 300, NULL, NULL, 0, NULL);
276
277 hWnd2 = CreateWindowW(L"sysparamstest", L"sysparamstest", WS_OVERLAPPEDWINDOW,
278 200, 200, 300, 300, NULL, NULL, 0, NULL);
279
280 Test_NonClientMetrics();
281 Test_MouseSpeed();
282 Test_GradientCaptions();
283
284 DestroyWindow(hWnd1);
285 DestroyWindow(hWnd2);
286 UnregisterClassW(L"sysparamstest", 0);
287 }
288