2 * Unit tests for dc functions
4 * Copyright (c) 2005 Huw Davies
5 * Copyright (c) 2005 Dmitry Timoshkov
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #define WINVER 0x0501 /* request latest DEVMODE */
27 #include "wine/test.h"
34 static DWORD (WINAPI
*pSetLayout
)(HDC hdc
, DWORD layout
);
36 static void dump_region(HRGN hrgn
)
44 printf( "(null) region\n" );
47 if (!(size
= GetRegionData( hrgn
, 0, NULL
))) return;
48 if (!(data
= HeapAlloc( GetProcessHeap(), 0, size
))) return;
49 GetRegionData( hrgn
, size
, data
);
50 printf( "%d rects:", data
->rdh
.nCount
);
51 for (i
= 0, rect
= (RECT
*)data
->Buffer
; i
< data
->rdh
.nCount
; i
++, rect
++)
52 printf( " (%d,%d)-(%d,%d)", rect
->left
, rect
->top
, rect
->right
, rect
->bottom
);
54 HeapFree( GetProcessHeap(), 0, data
);
57 static void test_savedc_2(void)
65 hwnd
= CreateWindowExA(0, "static", "", WS_POPUP
, 0,0,100,100,
68 ShowWindow(hwnd
, SW_SHOW
);
71 hrgn
= CreateRectRgn(0, 0, 0, 0);
75 ok(hdc
!= NULL
, "GetDC failed\n");
77 ret
= GetClipBox(hdc
, &rc_clip
);
78 ok(ret
== SIMPLEREGION
|| broken(ret
== COMPLEXREGION
), "GetClipBox returned %d instead of SIMPLEREGION\n", ret
);
79 ret
= GetClipRgn(hdc
, hrgn
);
80 ok(ret
== 0, "GetClipRgn returned %d instead of 0\n", ret
);
81 ret
= GetRgnBox(hrgn
, &rc
);
82 ok(ret
== NULLREGION
, "GetRgnBox returned %d (%d,%d-%d,%d) instead of NULLREGION\n",
83 ret
, rc
.left
, rc
.top
, rc
.right
, rc
.bottom
);
84 /*dump_region(hrgn);*/
85 SetRect(&rc
, 0, 0, 100, 100);
86 ok(EqualRect(&rc
, &rc_clip
),
87 "rects are not equal: (%d,%d-%d,%d) - (%d,%d-%d,%d)\n",
88 rc
.left
, rc
.top
, rc
.right
, rc
.bottom
,
89 rc_clip
.left
, rc_clip
.top
, rc_clip
.right
, rc_clip
.bottom
);
94 ok(ret
== 1, "ret = %d\n", ret
);
97 ret
= IntersectClipRect(hdc
, 0, 0, 50, 50);
98 if (ret
== COMPLEXREGION
)
100 /* XP returns COMPLEXREGION although dump_region reports only 1 rect */
101 trace("Windows BUG: IntersectClipRect returned %d instead of SIMPLEREGION\n", ret
);
102 /* let's make sure that it's a simple region */
103 ret
= GetClipRgn(hdc
, hrgn
);
104 ok(ret
== 1, "GetClipRgn returned %d instead of 1\n", ret
);
108 ok(ret
== SIMPLEREGION
, "IntersectClipRect returned %d instead of SIMPLEREGION\n", ret
);
110 ret
= GetClipBox(hdc
, &rc_clip
);
111 ok(ret
== SIMPLEREGION
|| broken(ret
== COMPLEXREGION
), "GetClipBox returned %d instead of SIMPLEREGION\n", ret
);
112 SetRect(&rc
, 0, 0, 50, 50);
113 ok(EqualRect(&rc
, &rc_clip
),
114 "rects are not equal: (%d,%d-%d,%d) - (%d,%d-%d,%d)\n",
115 rc
.left
, rc
.top
, rc
.right
, rc
.bottom
,
116 rc_clip
.left
, rc_clip
.top
, rc_clip
.right
, rc_clip
.bottom
);
118 ret
= RestoreDC(hdc
, 1);
119 ok(ret
, "ret = %d\n", ret
);
121 ret
= GetClipBox(hdc
, &rc_clip
);
122 ok(ret
== SIMPLEREGION
|| broken(ret
== COMPLEXREGION
), "GetClipBox returned %d instead of SIMPLEREGION\n", ret
);
123 SetRect(&rc
, 0, 0, 100, 100);
124 ok(EqualRect(&rc
, &rc_clip
),
125 "rects are not equal: (%d,%d-%d,%d) - (%d,%d-%d,%d)\n",
126 rc
.left
, rc
.top
, rc
.right
, rc
.bottom
,
127 rc_clip
.left
, rc_clip
.top
, rc_clip
.right
, rc_clip
.bottom
);
130 ReleaseDC(hwnd
, hdc
);
134 static void test_savedc(void)
136 HDC hdc
= CreateDCA("DISPLAY", NULL
, NULL
, NULL
);
139 ok(hdc
!= NULL
, "CreateDC rets %p\n", hdc
);
142 ok(ret
== 1, "ret = %d\n", ret
);
144 ok(ret
== 2, "ret = %d\n", ret
);
146 ok(ret
== 3, "ret = %d\n", ret
);
147 ret
= RestoreDC(hdc
, -1);
148 ok(ret
, "ret = %d\n", ret
);
150 ok(ret
== 3, "ret = %d\n", ret
);
151 ret
= RestoreDC(hdc
, 1);
152 ok(ret
, "ret = %d\n", ret
);
154 ok(ret
== 1, "ret = %d\n", ret
);
156 ok(ret
== 2, "ret = %d\n", ret
);
158 ok(ret
== 3, "ret = %d\n", ret
);
159 ret
= RestoreDC(hdc
, -2);
160 ok(ret
, "ret = %d\n", ret
);
162 ok(ret
== 2, "ret = %d\n", ret
);
163 ret
= RestoreDC(hdc
, -2);
164 ok(ret
, "ret = %d\n", ret
);
166 ok(ret
== 1, "ret = %d\n", ret
);
168 ok(ret
== 2, "ret = %d\n", ret
);
169 ret
= RestoreDC(hdc
, -4);
170 ok(!ret
, "ret = %d\n", ret
);
171 ret
= RestoreDC(hdc
, 3);
172 ok(!ret
, "ret = %d\n", ret
);
174 /* Under Win9x the following RestoreDC call succeeds and clears the save stack. */
175 ret
= RestoreDC(hdc
, -3);
177 broken(ret
), /* Win9x */
180 /* Trying to clear an empty save stack fails. */
181 ret
= RestoreDC(hdc
, -3);
182 ok(!ret
, "ret = %d\n", ret
);
186 broken(ret
== 1), /* Win9x */
189 /* Under Win9x the following RestoreDC call succeeds and clears the save stack. */
190 ret
= RestoreDC(hdc
, 0);
192 broken(ret
), /* Win9x */
195 /* Trying to clear an empty save stack fails. */
196 ret
= RestoreDC(hdc
, 0);
197 ok(!ret
, "ret = %d\n", ret
);
199 ret
= RestoreDC(hdc
, 1);
201 broken(!ret
), /* Win9x */
207 static void test_GdiConvertToDevmodeW(void)
209 DEVMODEW
* (WINAPI
*pGdiConvertToDevmodeW
)(const DEVMODEA
*);
214 pGdiConvertToDevmodeW
= (void *)GetProcAddress(GetModuleHandleA("gdi32.dll"), "GdiConvertToDevmodeW");
215 if (!pGdiConvertToDevmodeW
)
217 win_skip("GdiConvertToDevmodeW is not available on this platform\n");
221 ret
= EnumDisplaySettingsA(NULL
, ENUM_CURRENT_SETTINGS
, &dmA
);
222 ok(ret
, "EnumDisplaySettingsExA error %u\n", GetLastError());
223 ok(dmA
.dmSize
>= FIELD_OFFSET(DEVMODEA
, dmICMMethod
), "dmSize is too small: %04x\n", dmA
.dmSize
);
224 ok(dmA
.dmSize
<= sizeof(DEVMODEA
), "dmSize is too large: %04x\n", dmA
.dmSize
);
226 dmW
= pGdiConvertToDevmodeW(&dmA
);
227 ok(dmW
->dmSize
>= FIELD_OFFSET(DEVMODEW
, dmICMMethod
), "dmSize is too small: %04x\n", dmW
->dmSize
);
228 ok(dmW
->dmSize
<= sizeof(DEVMODEW
), "dmSize is too large: %04x\n", dmW
->dmSize
);
229 HeapFree(GetProcessHeap(), 0, dmW
);
231 dmA
.dmSize
= FIELD_OFFSET(DEVMODEA
, dmFields
) + sizeof(dmA
.dmFields
);
232 dmW
= pGdiConvertToDevmodeW(&dmA
);
233 ok(dmW
->dmSize
== FIELD_OFFSET(DEVMODEW
, dmFields
) + sizeof(dmW
->dmFields
),
234 "wrong size %u\n", dmW
->dmSize
);
235 HeapFree(GetProcessHeap(), 0, dmW
);
237 dmA
.dmICMMethod
= DMICMMETHOD_NONE
;
238 dmA
.dmSize
= FIELD_OFFSET(DEVMODEA
, dmICMMethod
) + sizeof(dmA
.dmICMMethod
);
239 dmW
= pGdiConvertToDevmodeW(&dmA
);
240 ok(dmW
->dmSize
== FIELD_OFFSET(DEVMODEW
, dmICMMethod
) + sizeof(dmW
->dmICMMethod
),
241 "wrong size %u\n", dmW
->dmSize
);
242 ok(dmW
->dmICMMethod
== DMICMMETHOD_NONE
,
243 "expected DMICMMETHOD_NONE, got %u\n", dmW
->dmICMMethod
);
244 HeapFree(GetProcessHeap(), 0, dmW
);
247 dmW
= pGdiConvertToDevmodeW(&dmA
);
248 ok(dmW
->dmSize
== FIELD_OFFSET(DEVMODEW
, dmPanningHeight
) + sizeof(dmW
->dmPanningHeight
),
249 "wrong size %u\n", dmW
->dmSize
);
250 HeapFree(GetProcessHeap(), 0, dmW
);
252 SetLastError(0xdeadbeef);
254 dmW
= pGdiConvertToDevmodeW(&dmA
);
255 ok(!dmW
, "GdiConvertToDevmodeW should fail\n");
256 ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %u\n", GetLastError());
258 /* this is the minimal dmSize that XP accepts */
259 dmA
.dmSize
= FIELD_OFFSET(DEVMODEA
, dmFields
);
260 dmW
= pGdiConvertToDevmodeW(&dmA
);
261 ok(dmW
->dmSize
== FIELD_OFFSET(DEVMODEW
, dmFields
),
262 "expected %04x, got %04x\n", FIELD_OFFSET(DEVMODEW
, dmFields
), dmW
->dmSize
);
263 HeapFree(GetProcessHeap(), 0, dmW
);
266 static void test_CreateCompatibleDC(void)
269 HDC hdc
, hNewDC
, hdcMetafile
;
273 bitmap
= CreateBitmap( 10, 10, 1, 1, NULL
);
275 /* Create a DC compatible with the screen */
276 hdc
= CreateCompatibleDC(NULL
);
277 ok(hdc
!= NULL
, "CreateCompatibleDC returned %p\n", hdc
);
278 ok( SelectObject( hdc
, bitmap
) != 0, "SelectObject failed\n" );
279 caps
= GetDeviceCaps( hdc
, TECHNOLOGY
);
280 ok( caps
== DT_RASDISPLAY
, "wrong caps %u\n", caps
);
282 /* Delete this DC, this should succeed */
283 bRet
= DeleteDC(hdc
);
284 ok(bRet
== TRUE
, "DeleteDC returned %u\n", bRet
);
286 /* Try to create a DC compatible to the deleted DC. This has to fail */
287 hNewDC
= CreateCompatibleDC(hdc
);
288 ok(hNewDC
== NULL
, "CreateCompatibleDC returned %p\n", hNewDC
);
291 hdcMetafile
= CreateEnhMetaFileA(hdc
, NULL
, NULL
, NULL
);
292 ok(hdcMetafile
!= 0, "CreateEnhMetaFileA failed\n");
293 hNewDC
= CreateCompatibleDC( hdcMetafile
);
294 ok(hNewDC
!= NULL
, "CreateCompatibleDC failed\n");
295 ok( SelectObject( hNewDC
, bitmap
) != 0, "SelectObject failed\n" );
296 caps
= GetDeviceCaps( hdcMetafile
, TECHNOLOGY
);
297 ok( caps
== DT_RASDISPLAY
, "wrong caps %u\n", caps
);
298 caps
= GetDeviceCaps( hNewDC
, TECHNOLOGY
);
299 ok( caps
== DT_RASDISPLAY
, "wrong caps %u\n", caps
);
301 DeleteEnhMetaFile( CloseEnhMetaFile( hdcMetafile
));
304 hdcMetafile
= CreateMetaFileA(NULL
);
305 ok(hdcMetafile
!= 0, "CreateEnhMetaFileA failed\n");
306 hNewDC
= CreateCompatibleDC( hdcMetafile
);
307 ok(hNewDC
== NULL
, "CreateCompatibleDC succeeded\n");
308 caps
= GetDeviceCaps( hdcMetafile
, TECHNOLOGY
);
309 ok( caps
== DT_METAFILE
, "wrong caps %u\n", caps
);
310 DeleteMetaFile( CloseMetaFile( hdcMetafile
));
312 DeleteObject( bitmap
);
315 static void test_DC_bitmap(void)
319 HBITMAP hbmp
, oldhbmp
;
323 /* fill bitmap data with b&w pattern */
324 for( i
= 0; i
< 64; i
++) bits
[i
] = i
& 1 ? 0 : 0xffffff;
327 ok( hdc
!= NULL
, "CreateDC rets %p\n", hdc
);
328 bitspixel
= GetDeviceCaps( hdc
, BITSPIXEL
);
329 /* create a memory dc */
330 hdcmem
= CreateCompatibleDC( hdc
);
331 ok( hdcmem
!= NULL
, "CreateCompatibleDC rets %p\n", hdcmem
);
333 /* test monochrome bitmap: should always work */
334 hbmp
= CreateBitmap(32, 32, 1, 1, bits
);
335 ok( hbmp
!= NULL
, "CreateBitmap returns %p\n", hbmp
);
336 oldhbmp
= SelectObject( hdcmem
, hbmp
);
337 ok( oldhbmp
!= NULL
, "SelectObject returned NULL\n" ); /* a memdc always has a bitmap selected */
338 col
= GetPixel( hdcmem
, 0, 0);
339 ok( col
== 0xffffff, "GetPixel returned %08x, expected 00ffffff\n", col
);
340 col
= GetPixel( hdcmem
, 1, 1);
341 ok( col
== 0x000000, "GetPixel returned %08x, expected 00000000\n", col
);
342 col
= GetPixel( hdcmem
, 100, 1);
343 ok( col
== CLR_INVALID
, "GetPixel returned %08x, expected ffffffff\n", col
);
344 SelectObject( hdcmem
, oldhbmp
);
347 /* test with 2 bits color depth, not likely to succeed */
348 hbmp
= CreateBitmap(16, 16, 1, 2, bits
);
349 ok( hbmp
!= NULL
, "CreateBitmap returns %p\n", hbmp
);
350 oldhbmp
= SelectObject( hdcmem
, hbmp
);
352 ok( !oldhbmp
, "SelectObject of a bitmap with 2 bits/pixel should return NULL\n");
353 if( oldhbmp
) SelectObject( hdcmem
, oldhbmp
);
356 /* test with 16 bits color depth, might succeed */
357 hbmp
= CreateBitmap(6, 6, 1, 16, bits
);
358 ok( hbmp
!= NULL
, "CreateBitmap returns %p\n", hbmp
);
359 oldhbmp
= SelectObject( hdcmem
, hbmp
);
360 if( bitspixel
== 16) {
361 ok( oldhbmp
!= NULL
, "SelectObject returned NULL\n" );
362 col
= GetPixel( hdcmem
, 0, 0);
364 "GetPixel of a bitmap with 16 bits/pixel returned %08x, expected 00ffffff\n", col
);
365 col
= GetPixel( hdcmem
, 1, 1);
367 "GetPixel of a bitmap with 16 bits/pixel returned returned %08x, expected 00000000\n", col
);
369 if( oldhbmp
) SelectObject( hdcmem
, oldhbmp
);
372 /* test with 32 bits color depth, probably succeed */
373 hbmp
= CreateBitmap(4, 4, 1, 32, bits
);
374 ok( hbmp
!= NULL
, "CreateBitmap returns %p\n", hbmp
);
375 oldhbmp
= SelectObject( hdcmem
, hbmp
);
376 if( bitspixel
== 32) {
377 ok( oldhbmp
!= NULL
, "SelectObject returned NULL\n" );
378 col
= GetPixel( hdcmem
, 0, 0);
380 "GetPixel of a bitmap with 32 bits/pixel returned %08x, expected 00ffffff\n", col
);
381 col
= GetPixel( hdcmem
, 1, 1);
383 "GetPixel of a bitmap with 32 bits/pixel returned returned %08x, expected 00000000\n", col
);
385 if( oldhbmp
) SelectObject( hdcmem
, oldhbmp
);
390 static void test_DeleteDC(void)
398 hwnd
= CreateWindowExA(0, "static", NULL
, WS_POPUP
|WS_VISIBLE
, 0,0,100,100,
400 ok(hwnd
!= 0, "CreateWindowExA failed\n");
403 ok(hdc
!= 0, "GetDC failed\n");
404 ret
= GetObjectType(hdc
);
405 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
407 ok(ret
, "DeleteDC failed\n");
408 ret
= GetObjectType(hdc
);
409 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
411 hdc
= GetWindowDC(hwnd
);
412 ok(hdc
!= 0, "GetDC failed\n");
413 ret
= GetObjectType(hdc
);
414 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
416 ok(ret
, "DeleteDC failed\n");
417 ret
= GetObjectType(hdc
);
418 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
422 /* desktop window DC */
423 hwnd
= GetDesktopWindow();
424 ok(hwnd
!= 0, "GetDesktopWindow failed\n");
427 ok(hdc
!= 0, "GetDC failed\n");
428 ret
= GetObjectType(hdc
);
429 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
431 ok(ret
, "DeleteDC failed\n");
432 ret
= GetObjectType(hdc
);
433 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
435 hdc
= GetWindowDC(hwnd
);
436 ok(hdc
!= 0, "GetDC failed\n");
437 ret
= GetObjectType(hdc
);
438 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
440 ok(ret
, "DeleteDC failed\n");
441 ret
= GetObjectType(hdc
);
442 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
445 memset(&cls
, 0, sizeof(cls
));
446 cls
.cbSize
= sizeof(cls
);
447 cls
.style
= CS_CLASSDC
;
448 cls
.hInstance
= GetModuleHandle(0);
449 cls
.lpszClassName
= "Wine class DC";
450 cls
.lpfnWndProc
= DefWindowProcA
;
451 ret
= RegisterClassExA(&cls
);
452 ok(ret
, "RegisterClassExA failed\n");
454 hwnd
= CreateWindowExA(0, "Wine class DC", NULL
, WS_POPUP
|WS_VISIBLE
, 0,0,100,100,
456 ok(hwnd
!= 0, "CreateWindowExA failed\n");
459 ok(hdc
!= 0, "GetDC failed\n");
460 ret
= GetObjectType(hdc
);
461 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
463 ok(ret
, "DeleteDC failed\n");
464 ret
= GetObjectType(hdc
);
465 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
466 ret
= ReleaseDC(hwnd
, hdc
);
467 ok(ret
, "ReleaseDC failed\n");
468 ret
= GetObjectType(hdc
);
469 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
473 hdc
= GetWindowDC(hwnd
);
474 ok(hdc
!= 0, "GetDC failed\n");
475 ret
= GetObjectType(hdc
);
476 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
478 ok(ret
, "DeleteDC failed\n");
479 ret
= GetObjectType(hdc
);
480 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
484 ret
= GetObjectType(hdc_test
);
485 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
487 ret
= UnregisterClassA("Wine class DC", GetModuleHandle(NULL
));
488 ok(ret
, "UnregisterClassA failed\n");
490 ret
= GetObjectType(hdc_test
);
492 ok(!ret
, "GetObjectType should fail for a deleted DC\n");
495 memset(&cls
, 0, sizeof(cls
));
496 cls
.cbSize
= sizeof(cls
);
497 cls
.style
= CS_OWNDC
;
498 cls
.hInstance
= GetModuleHandle(0);
499 cls
.lpszClassName
= "Wine own DC";
500 cls
.lpfnWndProc
= DefWindowProcA
;
501 ret
= RegisterClassExA(&cls
);
502 ok(ret
, "RegisterClassExA failed\n");
504 hwnd
= CreateWindowExA(0, "Wine own DC", NULL
, WS_POPUP
|WS_VISIBLE
, 0,0,100,100,
506 ok(hwnd
!= 0, "CreateWindowExA failed\n");
509 ok(hdc
!= 0, "GetDC failed\n");
510 ret
= GetObjectType(hdc
);
511 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
513 ok(ret
, "DeleteDC failed\n");
514 ret
= GetObjectType(hdc
);
515 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
516 ret
= ReleaseDC(hwnd
, hdc
);
517 ok(ret
, "ReleaseDC failed\n");
518 ret
= GetObjectType(hdc
);
519 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
521 hdc
= GetWindowDC(hwnd
);
522 ok(hdc
!= 0, "GetDC failed\n");
523 ret
= GetObjectType(hdc
);
524 ok(ret
== OBJ_DC
, "expected OBJ_DC, got %d\n", ret
);
526 ok(ret
, "DeleteDC failed\n");
527 ret
= GetObjectType(hdc
);
528 ok(!ret
|| broken(ret
) /* win9x */, "GetObjectType should fail for a deleted DC\n");
532 ret
= UnregisterClassA("Wine own DC", GetModuleHandle(NULL
));
533 ok(ret
, "UnregisterClassA failed\n");
536 static void test_boundsrect(void)
540 RECT rect
, expect
, set_rect
;
543 hdc
= CreateCompatibleDC(0);
544 ok(hdc
!= NULL
, "CreateCompatibleDC failed\n");
545 bitmap
= CreateCompatibleBitmap( hdc
, 200, 200 );
546 SelectObject( hdc
, bitmap
);
548 ret
= GetBoundsRect(hdc
, NULL
, 0);
549 ok(ret
== 0, "Expected GetBoundsRect to return 0, got %u\n", ret
);
551 ret
= GetBoundsRect(hdc
, NULL
, ~0U);
552 ok(ret
== 0, "Expected GetBoundsRect to return 0, got %u\n", ret
);
554 /* Test parameter handling order. */
555 SetRect(&set_rect
, 10, 20, 40, 50);
556 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
558 "Expected return flag DCB_RESET to be set, got %u\n", ret
);
560 ret
= GetBoundsRect(hdc
, NULL
, DCB_RESET
);
562 "Expected GetBoundsRect to return 0, got %u\n", ret
);
564 ret
= GetBoundsRect(hdc
, &rect
, 0);
566 "Expected GetBoundsRect to return DCB_RESET, got %u\n", ret
);
567 SetRect(&expect
, 0, 0, 0, 0);
568 ok(EqualRect(&rect
, &expect
) ||
569 broken(EqualRect(&rect
, &set_rect
)), /* nt4 sp1-5 */
570 "Expected output rectangle (0,0)-(0,0), got (%d,%d)-(%d,%d)\n",
571 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
573 ret
= GetBoundsRect(NULL
, NULL
, 0);
574 ok(ret
== 0, "Expected GetBoundsRect to return 0, got %u\n", ret
);
576 ret
= GetBoundsRect(NULL
, NULL
, ~0U);
577 ok(ret
== 0, "Expected GetBoundsRect to return 0, got %u\n", ret
);
579 ret
= SetBoundsRect(NULL
, NULL
, 0);
580 ok(ret
== 0, "Expected SetBoundsRect to return 0, got %u\n", ret
);
582 ret
= SetBoundsRect(NULL
, NULL
, ~0U);
583 ok(ret
== 0, "Expected SetBoundsRect to return 0, got %u\n", ret
);
585 SetRect(&set_rect
, 10, 20, 40, 50);
586 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
587 ok(ret
== (DCB_RESET
| DCB_DISABLE
), "SetBoundsRect returned %x\n", ret
);
589 ret
= GetBoundsRect(hdc
, &rect
, 0);
590 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
591 SetRect(&expect
, 10, 20, 40, 50);
592 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
593 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
595 SetMapMode( hdc
, MM_ANISOTROPIC
);
596 SetViewportExtEx( hdc
, 2, 2, NULL
);
597 ret
= GetBoundsRect(hdc
, &rect
, 0);
598 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
599 SetRect(&expect
, 5, 10, 20, 25);
600 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
601 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
603 SetViewportOrgEx( hdc
, 20, 30, NULL
);
604 ret
= GetBoundsRect(hdc
, &rect
, 0);
605 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
606 SetRect(&expect
, -5, -5, 10, 10);
607 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
608 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
610 SetRect(&set_rect
, 10, 20, 40, 50);
611 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
612 ok(ret
== (DCB_SET
| DCB_DISABLE
), "SetBoundsRect returned %x\n", ret
);
614 ret
= GetBoundsRect(hdc
, &rect
, 0);
615 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
616 SetRect(&expect
, 10, 20, 40, 50);
617 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
618 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
620 SetMapMode( hdc
, MM_TEXT
);
621 SetViewportOrgEx( hdc
, 0, 0, NULL
);
622 ret
= GetBoundsRect(hdc
, &rect
, 0);
623 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
624 SetRect(&expect
, 40, 70, 100, 130);
625 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
626 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
630 pSetLayout( hdc
, LAYOUT_RTL
);
631 ret
= GetBoundsRect(hdc
, &rect
, 0);
632 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
633 SetRect(&expect
, 159, 70, 99, 130);
634 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
635 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
636 SetRect(&set_rect
, 50, 25, 30, 35);
637 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
638 ok(ret
== (DCB_SET
| DCB_DISABLE
), "SetBoundsRect returned %x\n", ret
);
639 ret
= GetBoundsRect(hdc
, &rect
, 0);
640 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
641 SetRect(&expect
, 50, 25, 30, 35);
642 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
643 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
645 pSetLayout( hdc
, LAYOUT_LTR
);
646 ret
= GetBoundsRect(hdc
, &rect
, 0);
647 ok(ret
== DCB_SET
, "GetBoundsRect returned %x\n", ret
);
648 SetRect(&expect
, 149, 25, 169, 35);
649 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
650 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
653 /* empty rect resets, except on nt4 */
654 SetRect(&expect
, 20, 20, 10, 10);
655 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
656 ok(ret
== (DCB_SET
| DCB_DISABLE
), "SetBoundsRect returned %x\n", ret
);
657 ret
= GetBoundsRect(hdc
, &rect
, 0);
658 ok(ret
== DCB_RESET
|| broken(ret
== DCB_SET
) /* nt4 */,
659 "GetBoundsRect returned %x\n", ret
);
660 if (ret
== DCB_RESET
)
662 SetRect(&expect
, 0, 0, 0, 0);
663 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
664 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
666 SetRect(&expect
, 20, 20, 20, 20);
667 ret
= SetBoundsRect(hdc
, &set_rect
, DCB_SET
);
668 ok(ret
== (DCB_RESET
| DCB_DISABLE
), "SetBoundsRect returned %x\n", ret
);
669 ret
= GetBoundsRect(hdc
, &rect
, 0);
670 ok(ret
== DCB_RESET
, "GetBoundsRect returned %x\n", ret
);
671 SetRect(&expect
, 0, 0, 0, 0);
672 ok(EqualRect(&rect
, &expect
), "Got (%d,%d)-(%d,%d)\n",
673 rect
.left
, rect
.top
, rect
.right
, rect
.bottom
);
677 DeleteObject( bitmap
);
680 static void test_desktop_colorres(void)
682 HDC hdc
= GetDC(NULL
);
683 int bitspixel
, colorres
;
685 bitspixel
= GetDeviceCaps(hdc
, BITSPIXEL
);
686 ok(bitspixel
!= 0, "Expected to get valid BITSPIXEL capability value\n");
688 colorres
= GetDeviceCaps(hdc
, COLORRES
);
690 broken(colorres
== 0), /* Win9x */
691 "Expected to get valid COLORRES capability value\n");
699 "Expected COLORRES to be 18, got %d\n", colorres
);
703 "Expected COLORRES to be 16, got %d\n", colorres
);
708 "Expected COLORRES to be 24, got %d\n", bitspixel
);
711 ok(0, "Got unknown BITSPIXEL %d with COLORRES %d\n", bitspixel
, colorres
);
716 ReleaseDC(NULL
, hdc
);
719 static void test_gamma(void)
722 HDC hdc
= GetDC(NULL
);
723 WORD oldramp
[3][256], ramp
[3][256];
726 ret
= GetDeviceGammaRamp(hdc
, &oldramp
);
729 win_skip("GetDeviceGammaRamp failed, skipping tests\n");
733 /* try to set back old ramp */
734 ret
= SetDeviceGammaRamp(hdc
, &oldramp
);
737 win_skip("SetDeviceGammaRamp failed, skipping tests\n");
741 memcpy(ramp
, oldramp
, sizeof(ramp
));
743 /* set one color ramp to zeros */
744 memset(ramp
[0], 0, sizeof(ramp
[0]));
745 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
746 ok(!ret
, "SetDeviceGammaRamp succeeded\n");
748 /* set one color ramp to a flat straight rising line */
749 for (i
= 0; i
< 256; i
++) ramp
[0][i
] = i
;
750 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
751 todo_wine
ok(!ret
, "SetDeviceGammaRamp succeeded\n");
753 /* set one color ramp to a steep straight rising line */
754 for (i
= 0; i
< 256; i
++) ramp
[0][i
] = i
* 256;
755 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
756 ok(ret
, "SetDeviceGammaRamp failed\n");
758 /* try a bright gamma ramp */
761 for (i
= 2; i
< 256; i
++) ramp
[0][i
] = 0xFFFF;
762 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
763 ok(!ret
, "SetDeviceGammaRamp succeeded\n");
765 /* try ramps which are not uniform */
767 for (i
= 1; i
< 256; i
++) ramp
[0][i
] = ramp
[0][i
- 1] + 512;
768 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
769 ok(ret
, "SetDeviceGammaRamp failed\n");
771 for (i
= 2; i
< 256; i
+=2)
773 ramp
[0][i
- 1] = ramp
[0][i
- 2];
774 ramp
[0][i
] = ramp
[0][i
- 2] + 512;
776 ret
= SetDeviceGammaRamp(hdc
, &ramp
);
777 ok(ret
, "SetDeviceGammaRamp failed\n");
779 /* cleanup: set old ramp again */
780 ret
= SetDeviceGammaRamp(hdc
, &oldramp
);
781 ok(ret
, "SetDeviceGammaRamp failed\n");
784 ReleaseDC(NULL
, hdc
);
787 static HDC
create_printer_dc(void)
791 PRINTER_INFO_2A
*pbuf
= NULL
;
792 DRIVER_INFO_3A
*dbuf
= NULL
;
795 HMODULE winspool
= LoadLibraryA( "winspool.drv" );
796 BOOL (WINAPI
*pOpenPrinterA
)(LPSTR
, HANDLE
*, LPPRINTER_DEFAULTSA
);
797 BOOL (WINAPI
*pGetDefaultPrinterA
)(LPSTR
, LPDWORD
);
798 BOOL (WINAPI
*pGetPrinterA
)(HANDLE
, DWORD
, LPBYTE
, DWORD
, LPDWORD
);
799 BOOL (WINAPI
*pGetPrinterDriverA
)(HANDLE
, LPSTR
, DWORD
, LPBYTE
, DWORD
, LPDWORD
);
800 BOOL (WINAPI
*pClosePrinter
)(HANDLE
);
802 pGetDefaultPrinterA
= (void *)GetProcAddress( winspool
, "GetDefaultPrinterA" );
803 pOpenPrinterA
= (void *)GetProcAddress( winspool
, "OpenPrinterA" );
804 pGetPrinterA
= (void *)GetProcAddress( winspool
, "GetPrinterA" );
805 pGetPrinterDriverA
= (void *)GetProcAddress( winspool
, "GetPrinterDriverA" );
806 pClosePrinter
= (void *)GetProcAddress( winspool
, "ClosePrinter" );
808 if (!pGetDefaultPrinterA
|| !pOpenPrinterA
|| !pGetPrinterA
|| !pGetPrinterDriverA
|| !pClosePrinter
)
811 len
= sizeof(buffer
);
812 if (!pGetDefaultPrinterA( buffer
, &len
)) goto done
;
813 if (!pOpenPrinterA( buffer
, &hprn
, NULL
)) goto done
;
815 pGetPrinterA( hprn
, 2, NULL
, 0, &len
);
816 pbuf
= HeapAlloc( GetProcessHeap(), 0, len
);
817 if (!pGetPrinterA( hprn
, 2, (LPBYTE
)pbuf
, len
, &len
)) goto done
;
819 pGetPrinterDriverA( hprn
, NULL
, 3, NULL
, 0, &len
);
820 dbuf
= HeapAlloc( GetProcessHeap(), 0, len
);
821 if (!pGetPrinterDriverA( hprn
, NULL
, 3, (LPBYTE
)dbuf
, len
, &len
)) goto done
;
823 hdc
= CreateDCA( dbuf
->pDriverPath
, pbuf
->pPrinterName
, pbuf
->pPortName
, pbuf
->pDevMode
);
824 trace( "hdc %p for driver '%s' printer '%s' port '%s'\n", hdc
,
825 dbuf
->pDriverPath
, pbuf
->pPrinterName
, pbuf
->pPortName
);
827 HeapFree( GetProcessHeap(), 0, dbuf
);
828 HeapFree( GetProcessHeap(), 0, pbuf
);
829 if (hprn
) pClosePrinter( hprn
);
830 if (winspool
) FreeLibrary( winspool
);
831 if (!hdc
) skip( "could not create a DC for the default printer\n" );
835 static void test_printer_dc(void)
837 HDC memdc
, display_memdc
;
840 HDC hdc
= create_printer_dc();
844 memdc
= CreateCompatibleDC( hdc
);
845 display_memdc
= CreateCompatibleDC( 0 );
847 ok( memdc
!= NULL
, "CreateCompatibleDC failed for printer\n" );
848 ok( display_memdc
!= NULL
, "CreateCompatibleDC failed for screen\n" );
850 ret
= GetDeviceCaps( hdc
, TECHNOLOGY
);
851 ok( ret
== DT_RASPRINTER
, "wrong type %u\n", ret
);
853 ret
= GetDeviceCaps( memdc
, TECHNOLOGY
);
854 ok( ret
== DT_RASPRINTER
, "wrong type %u\n", ret
);
856 ret
= GetDeviceCaps( display_memdc
, TECHNOLOGY
);
857 ok( ret
== DT_RASDISPLAY
, "wrong type %u\n", ret
);
859 bmp
= CreateBitmap( 100, 100, 1, GetDeviceCaps( hdc
, BITSPIXEL
), NULL
);
860 orig
= SelectObject( memdc
, bmp
);
861 ok( orig
!= NULL
, "SelectObject failed\n" );
862 ok( BitBlt( hdc
, 10, 10, 20, 20, memdc
, 0, 0, SRCCOPY
), "BitBlt failed\n" );
864 ok( !SelectObject( display_memdc
, bmp
), "SelectObject succeeded\n" );
865 SelectObject( memdc
, orig
);
868 bmp
= CreateBitmap( 100, 100, 1, 1, NULL
);
869 orig
= SelectObject( display_memdc
, bmp
);
870 ok( orig
!= NULL
, "SelectObject failed\n" );
871 ok( !SelectObject( memdc
, bmp
), "SelectObject succeeded\n" );
872 ok( BitBlt( hdc
, 10, 10, 20, 20, display_memdc
, 0, 0, SRCCOPY
), "BitBlt failed\n" );
873 ok( BitBlt( memdc
, 10, 10, 20, 20, display_memdc
, 0, 0, SRCCOPY
), "BitBlt failed\n" );
874 ok( BitBlt( display_memdc
, 10, 10, 20, 20, memdc
, 0, 0, SRCCOPY
), "BitBlt failed\n" );
876 ret
= GetPixel( hdc
, 0, 0 );
877 ok( ret
== CLR_INVALID
, "wrong pixel value %x\n", ret
);
880 DeleteDC( display_memdc
);
887 pSetLayout
= (void *)GetProcAddress( GetModuleHandle("gdi32.dll"), "SetLayout");
890 test_GdiConvertToDevmodeW();
891 test_CreateCompatibleDC();
895 test_desktop_colorres();