dinput: BuildActionMap and SetActionMap stubs for generic joystick.
[wine] / dlls / gdiplus / tests / graphics.c
1 /*
2  * Unit test suite for graphics objects
3  *
4  * Copyright (C) 2007 Google (Evan Stade)
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20
21 #include "windows.h"
22 #include "gdiplus.h"
23 #include "wingdi.h"
24 #include "wine/test.h"
25 #include <math.h>
26
27 #define expect(expected, got) ok(got == expected, "Expected %.8x, got %.8x\n", expected, got)
28 #define expectf_(expected, got, precision) ok(fabs(expected - got) < precision, "Expected %.2f, got %.2f\n", expected, got)
29 #define expectf(expected, got) expectf_(expected, got, 0.0001)
30 #define TABLE_LEN (23)
31
32 static HWND hwnd;
33
34 static void test_constructor_destructor(void)
35 {
36     GpStatus stat;
37     GpGraphics *graphics = NULL;
38     HDC hdc = GetDC( hwnd );
39
40     stat = GdipCreateFromHDC(NULL, &graphics);
41     expect(OutOfMemory, stat);
42     stat = GdipDeleteGraphics(graphics);
43     expect(InvalidParameter, stat);
44
45     stat = GdipCreateFromHDC(hdc, &graphics);
46     expect(Ok, stat);
47     stat = GdipDeleteGraphics(graphics);
48     expect(Ok, stat);
49
50     stat = GdipCreateFromHWND(NULL, &graphics);
51     expect(Ok, stat);
52     stat = GdipDeleteGraphics(graphics);
53     expect(Ok, stat);
54
55     stat = GdipCreateFromHWNDICM(NULL, &graphics);
56     expect(Ok, stat);
57     stat = GdipDeleteGraphics(graphics);
58     expect(Ok, stat);
59
60     stat = GdipDeleteGraphics(NULL);
61     expect(InvalidParameter, stat);
62     ReleaseDC(hwnd, hdc);
63 }
64
65 typedef struct node{
66     GraphicsState data;
67     struct node * next;
68 } node;
69
70 /* Linked list prepend function. */
71 static void log_state(GraphicsState data, node ** log)
72 {
73     node * new_entry = HeapAlloc(GetProcessHeap(), 0, sizeof(node));
74
75     new_entry->data = data;
76     new_entry->next = *log;
77     *log = new_entry;
78 }
79
80 /* Checks if there are duplicates in the list, and frees it. */
81 static void check_no_duplicates(node * log)
82 {
83     INT dups = 0;
84     node * temp = NULL;
85     node * temp2 = NULL;
86     node * orig = log;
87
88     if(!log)
89         goto end;
90
91     do{
92         temp = log;
93         while((temp = temp->next)){
94             if(log->data == temp->data){
95                 dups++;
96                 break;
97             }
98             if(dups > 0)
99                 break;
100         }
101     }while((log = log->next));
102
103     temp = orig;
104     do{
105         temp2 = temp->next;
106         HeapFree(GetProcessHeap(), 0, temp);
107         temp = temp2;
108     }while(temp);
109
110 end:
111     expect(0, dups);
112 }
113
114 static void test_save_restore(void)
115 {
116     GpStatus stat;
117     GraphicsState state_a, state_b, state_c;
118     InterpolationMode mode;
119     GpGraphics *graphics1, *graphics2;
120     node * state_log = NULL;
121     HDC hdc = GetDC( hwnd );
122     state_a = state_b = state_c = 0xdeadbeef;
123
124     /* Invalid saving. */
125     GdipCreateFromHDC(hdc, &graphics1);
126     stat = GdipSaveGraphics(graphics1, NULL);
127     expect(InvalidParameter, stat);
128     stat = GdipSaveGraphics(NULL, &state_a);
129     expect(InvalidParameter, stat);
130     GdipDeleteGraphics(graphics1);
131
132     log_state(state_a, &state_log);
133
134     /* Basic save/restore. */
135     GdipCreateFromHDC(hdc, &graphics1);
136     GdipSetInterpolationMode(graphics1, InterpolationModeBilinear);
137     stat = GdipSaveGraphics(graphics1, &state_a);
138     expect(Ok, stat);
139     GdipSetInterpolationMode(graphics1, InterpolationModeBicubic);
140     stat = GdipRestoreGraphics(graphics1, state_a);
141     expect(Ok, stat);
142     GdipGetInterpolationMode(graphics1, &mode);
143     expect(InterpolationModeBilinear, mode);
144     GdipDeleteGraphics(graphics1);
145
146     log_state(state_a, &state_log);
147
148     /* Restoring garbage doesn't affect saves. */
149     GdipCreateFromHDC(hdc, &graphics1);
150     GdipSetInterpolationMode(graphics1, InterpolationModeBilinear);
151     GdipSaveGraphics(graphics1, &state_a);
152     GdipSetInterpolationMode(graphics1, InterpolationModeBicubic);
153     GdipSaveGraphics(graphics1, &state_b);
154     GdipSetInterpolationMode(graphics1, InterpolationModeNearestNeighbor);
155     stat = GdipRestoreGraphics(graphics1, 0xdeadbeef);
156     expect(Ok, stat);
157     GdipRestoreGraphics(graphics1, state_b);
158     GdipGetInterpolationMode(graphics1, &mode);
159     expect(InterpolationModeBicubic, mode);
160     GdipRestoreGraphics(graphics1, state_a);
161     GdipGetInterpolationMode(graphics1, &mode);
162     expect(InterpolationModeBilinear, mode);
163     GdipDeleteGraphics(graphics1);
164
165     log_state(state_a, &state_log);
166     log_state(state_b, &state_log);
167
168     /* Restoring older state invalidates newer saves (but not older saves). */
169     GdipCreateFromHDC(hdc, &graphics1);
170     GdipSetInterpolationMode(graphics1, InterpolationModeBilinear);
171     GdipSaveGraphics(graphics1, &state_a);
172     GdipSetInterpolationMode(graphics1, InterpolationModeBicubic);
173     GdipSaveGraphics(graphics1, &state_b);
174     GdipSetInterpolationMode(graphics1, InterpolationModeNearestNeighbor);
175     GdipSaveGraphics(graphics1, &state_c);
176     GdipSetInterpolationMode(graphics1, InterpolationModeHighQualityBilinear);
177     GdipRestoreGraphics(graphics1, state_b);
178     GdipGetInterpolationMode(graphics1, &mode);
179     expect(InterpolationModeBicubic, mode);
180     GdipRestoreGraphics(graphics1, state_c);
181     GdipGetInterpolationMode(graphics1, &mode);
182     expect(InterpolationModeBicubic, mode);
183     GdipRestoreGraphics(graphics1, state_a);
184     GdipGetInterpolationMode(graphics1, &mode);
185     expect(InterpolationModeBilinear, mode);
186     GdipDeleteGraphics(graphics1);
187
188     log_state(state_a, &state_log);
189     log_state(state_b, &state_log);
190     log_state(state_c, &state_log);
191
192     /* Restoring older save from one graphics object does not invalidate
193      * newer save from other graphics object. */
194     GdipCreateFromHDC(hdc, &graphics1);
195     GdipCreateFromHDC(hdc, &graphics2);
196     GdipSetInterpolationMode(graphics1, InterpolationModeBilinear);
197     GdipSaveGraphics(graphics1, &state_a);
198     GdipSetInterpolationMode(graphics2, InterpolationModeBicubic);
199     GdipSaveGraphics(graphics2, &state_b);
200     GdipSetInterpolationMode(graphics1, InterpolationModeNearestNeighbor);
201     GdipSetInterpolationMode(graphics2, InterpolationModeNearestNeighbor);
202     GdipRestoreGraphics(graphics1, state_a);
203     GdipGetInterpolationMode(graphics1, &mode);
204     expect(InterpolationModeBilinear, mode);
205     GdipRestoreGraphics(graphics2, state_b);
206     GdipGetInterpolationMode(graphics2, &mode);
207     expect(InterpolationModeBicubic, mode);
208     GdipDeleteGraphics(graphics1);
209     GdipDeleteGraphics(graphics2);
210
211     /* You can't restore a state to a graphics object that didn't save it. */
212     GdipCreateFromHDC(hdc, &graphics1);
213     GdipCreateFromHDC(hdc, &graphics2);
214     GdipSetInterpolationMode(graphics1, InterpolationModeBilinear);
215     GdipSaveGraphics(graphics1, &state_a);
216     GdipSetInterpolationMode(graphics1, InterpolationModeNearestNeighbor);
217     GdipSetInterpolationMode(graphics2, InterpolationModeNearestNeighbor);
218     GdipRestoreGraphics(graphics2, state_a);
219     GdipGetInterpolationMode(graphics2, &mode);
220     expect(InterpolationModeNearestNeighbor, mode);
221     GdipDeleteGraphics(graphics1);
222     GdipDeleteGraphics(graphics2);
223
224     log_state(state_a, &state_log);
225
226     /* The same state value should never be returned twice. */
227     todo_wine
228         check_no_duplicates(state_log);
229
230     ReleaseDC(hwnd, hdc);
231 }
232
233 static void test_GdipFillClosedCurve2(void)
234 {
235     GpStatus status;
236     GpGraphics *graphics = NULL;
237     GpSolidFill *brush = NULL;
238     HDC hdc = GetDC( hwnd );
239     GpPointF points[3];
240
241     points[0].X = 0;
242     points[0].Y = 0;
243
244     points[1].X = 40;
245     points[1].Y = 20;
246
247     points[2].X = 10;
248     points[2].Y = 40;
249
250     /* make a graphics object and brush object */
251     ok(hdc != NULL, "Expected HDC to be initialized\n");
252
253     status = GdipCreateFromHDC(hdc, &graphics);
254     expect(Ok, status);
255     ok(graphics != NULL, "Expected graphics to be initialized\n");
256
257     GdipCreateSolidFill((ARGB)0xdeadbeef, &brush);
258
259     /* InvalidParameter cases: null graphics, null brush, null points */
260     status = GdipFillClosedCurve2(NULL, NULL, NULL, 3, 0.5, FillModeAlternate);
261     expect(InvalidParameter, status);
262
263     status = GdipFillClosedCurve2(graphics, NULL, NULL, 3, 0.5, FillModeAlternate);
264     expect(InvalidParameter, status);
265
266     status = GdipFillClosedCurve2(NULL, (GpBrush*)brush, NULL, 3, 0.5, FillModeAlternate);
267     expect(InvalidParameter, status);
268
269     status = GdipFillClosedCurve2(NULL, NULL, points, 3, 0.5, FillModeAlternate);
270     expect(InvalidParameter, status);
271
272     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, NULL, 3, 0.5, FillModeAlternate);
273     expect(InvalidParameter, status);
274
275     status = GdipFillClosedCurve2(graphics, NULL, points, 3, 0.5, FillModeAlternate);
276     expect(InvalidParameter, status);
277
278     status = GdipFillClosedCurve2(NULL, (GpBrush*)brush, points, 3, 0.5, FillModeAlternate);
279     expect(InvalidParameter, status);
280
281     /* InvalidParameter cases: invalid count */
282     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, points, -1, 0.5, FillModeAlternate);
283     expect(InvalidParameter, status);
284
285     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, points, 0, 0.5, FillModeAlternate);
286     expect(InvalidParameter, status);
287
288     /* Valid test cases */
289     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, points, 1, 0.5, FillModeAlternate);
290     expect(Ok, status);
291
292     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, points, 2, 0.5, FillModeAlternate);
293     expect(Ok, status);
294
295     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, points, 3, 0.5, FillModeAlternate);
296     expect(Ok, status);
297
298     GdipDeleteGraphics(graphics);
299     GdipDeleteBrush((GpBrush*)brush);
300
301     ReleaseDC(hwnd, hdc);
302 }
303
304 static void test_GdipFillClosedCurve2I(void)
305 {
306     GpStatus status;
307     GpGraphics *graphics = NULL;
308     GpSolidFill *brush = NULL;
309     HDC hdc = GetDC( hwnd );
310     GpPoint points[3];
311
312     points[0].X = 0;
313     points[0].Y = 0;
314
315     points[1].X = 40;
316     points[1].Y = 20;
317
318     points[2].X = 10;
319     points[2].Y = 40;
320
321     /* make a graphics object and brush object */
322     ok(hdc != NULL, "Expected HDC to be initialized\n");
323
324     status = GdipCreateFromHDC(hdc, &graphics);
325     expect(Ok, status);
326     ok(graphics != NULL, "Expected graphics to be initialized\n");
327
328     GdipCreateSolidFill((ARGB)0xdeadbeef, &brush);
329
330     /* InvalidParameter cases: null graphics, null brush */
331     /* Note: GdipFillClosedCurveI and GdipFillClosedCurve2I hang in Windows
332              when points == NULL, so don't test this condition */
333     status = GdipFillClosedCurve2I(NULL, NULL, points, 3, 0.5, FillModeAlternate);
334     expect(InvalidParameter, status);
335
336     status = GdipFillClosedCurve2I(graphics, NULL, points, 3, 0.5, FillModeAlternate);
337     expect(InvalidParameter, status);
338
339     status = GdipFillClosedCurve2I(NULL, (GpBrush*)brush, points, 3, 0.5, FillModeAlternate);
340     expect(InvalidParameter, status);
341
342     /* InvalidParameter cases: invalid count */
343     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, points, 0, 0.5, FillModeAlternate);
344     expect(InvalidParameter, status);
345
346     /* OutOfMemory cases: large (unsigned) int */
347     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, points, -1, 0.5, FillModeAlternate);
348     expect(OutOfMemory, status);
349
350     /* Valid test cases */
351     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, points, 1, 0.5, FillModeAlternate);
352     expect(Ok, status);
353
354     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, points, 2, 0.5, FillModeAlternate);
355     expect(Ok, status);
356
357     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, points, 3, 0.5, FillModeAlternate);
358     expect(Ok, status);
359
360     GdipDeleteGraphics(graphics);
361     GdipDeleteBrush((GpBrush*)brush);
362
363     ReleaseDC(hwnd, hdc);
364 }
365
366 static void test_GdipDrawArc(void)
367 {
368     GpStatus status;
369     GpGraphics *graphics = NULL;
370     GpPen *pen = NULL;
371     HDC hdc = GetDC( hwnd );
372
373     /* make a graphics object and pen object */
374     ok(hdc != NULL, "Expected HDC to be initialized\n");
375
376     status = GdipCreateFromHDC(hdc, &graphics);
377     expect(Ok, status);
378     ok(graphics != NULL, "Expected graphics to be initialized\n");
379
380     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
381     expect(Ok, status);
382     ok(pen != NULL, "Expected pen to be initialized\n");
383
384     /* InvalidParameter cases: null graphics, null pen, non-positive width, non-positive height */
385     status = GdipDrawArc(NULL, NULL, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0);
386     expect(InvalidParameter, status);
387
388     status = GdipDrawArc(graphics, NULL, 0.0, 0.0, 1.0, 1.0, 0.0, 0.0);
389     expect(InvalidParameter, status);
390
391     status = GdipDrawArc(NULL, pen, 0.0, 0.0, 1.0, 1.0, 0.0, 0.0);
392     expect(InvalidParameter, status);
393
394     status = GdipDrawArc(graphics, pen, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0);
395     expect(InvalidParameter, status);
396
397     status = GdipDrawArc(graphics, pen, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0);
398     expect(InvalidParameter, status);
399
400     /* successful case */
401     status = GdipDrawArc(graphics, pen, 0.0, 0.0, 1.0, 1.0, 0.0, 0.0);
402     expect(Ok, status);
403
404     GdipDeletePen(pen);
405     GdipDeleteGraphics(graphics);
406
407     ReleaseDC(hwnd, hdc);
408 }
409
410 static void test_GdipDrawArcI(void)
411 {
412     GpStatus status;
413     GpGraphics *graphics = NULL;
414     GpPen *pen = NULL;
415     HDC hdc = GetDC( hwnd );
416
417     /* make a graphics object and pen object */
418     ok(hdc != NULL, "Expected HDC to be initialized\n");
419
420     status = GdipCreateFromHDC(hdc, &graphics);
421     expect(Ok, status);
422     ok(graphics != NULL, "Expected graphics to be initialized\n");
423
424     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
425     expect(Ok, status);
426     ok(pen != NULL, "Expected pen to be initialized\n");
427
428     /* InvalidParameter cases: null graphics, null pen, non-positive width, non-positive height */
429     status = GdipDrawArcI(NULL, NULL, 0, 0, 0, 0, 0, 0);
430     expect(InvalidParameter, status);
431
432     status = GdipDrawArcI(graphics, NULL, 0, 0, 1, 1, 0, 0);
433     expect(InvalidParameter, status);
434
435     status = GdipDrawArcI(NULL, pen, 0, 0, 1, 1, 0, 0);
436     expect(InvalidParameter, status);
437
438     status = GdipDrawArcI(graphics, pen, 0, 0, 1, 0, 0, 0);
439     expect(InvalidParameter, status);
440
441     status = GdipDrawArcI(graphics, pen, 0, 0, 0, 1, 0, 0);
442     expect(InvalidParameter, status);
443
444     /* successful case */
445     status = GdipDrawArcI(graphics, pen, 0, 0, 1, 1, 0, 0);
446     expect(Ok, status);
447
448     GdipDeletePen(pen);
449     GdipDeleteGraphics(graphics);
450
451     ReleaseDC(hwnd, hdc);
452 }
453
454 static void test_BeginContainer2(void)
455 {
456     GpMatrix *transform;
457     GpRectF clip;
458     REAL defClip[] = {5, 10, 15, 20};
459     REAL elems[6], defTrans[] = {1, 2, 3, 4, 5, 6};
460     GraphicsContainer cont1, cont2, cont3, cont4;
461     CompositingQuality compqual, defCompqual = CompositingQualityHighSpeed;
462     CompositingMode compmode, defCompmode = CompositingModeSourceOver;
463     InterpolationMode interp, defInterp = InterpolationModeHighQualityBicubic;
464     REAL scale, defScale = 17;
465     GpUnit unit, defUnit = UnitPixel;
466     PixelOffsetMode offsetmode, defOffsetmode = PixelOffsetModeHighSpeed;
467     SmoothingMode smoothmode, defSmoothmode = SmoothingModeAntiAlias;
468     UINT contrast, defContrast = 5;
469     TextRenderingHint texthint, defTexthint = TextRenderingHintAntiAlias;
470
471     GpStatus status;
472     GpGraphics *graphics = NULL;
473     HDC hdc = GetDC( hwnd );
474
475     ok(hdc != NULL, "Expected HDC to be initialized\n");
476
477     status = GdipCreateFromHDC(hdc, &graphics);
478     expect(Ok, status);
479     ok(graphics != NULL, "Expected graphics to be initialized\n");
480
481     /* null graphics, null container */
482     status = GdipBeginContainer2(NULL, &cont1);
483     expect(InvalidParameter, status);
484
485     status = GdipBeginContainer2(graphics, NULL);
486     expect(InvalidParameter, status);
487
488     status = GdipEndContainer(NULL, cont1);
489     expect(InvalidParameter, status);
490
491     /* test all quality-related values */
492     GdipSetCompositingMode(graphics, defCompmode);
493     GdipSetCompositingQuality(graphics, defCompqual);
494     GdipSetInterpolationMode(graphics, defInterp);
495     GdipSetPageScale(graphics, defScale);
496     GdipSetPageUnit(graphics, defUnit);
497     GdipSetPixelOffsetMode(graphics, defOffsetmode);
498     GdipSetSmoothingMode(graphics, defSmoothmode);
499     GdipSetTextContrast(graphics, defContrast);
500     GdipSetTextRenderingHint(graphics, defTexthint);
501
502     status = GdipBeginContainer2(graphics, &cont1);
503     expect(Ok, status);
504
505     GdipSetCompositingMode(graphics, CompositingModeSourceCopy);
506     GdipSetCompositingQuality(graphics, CompositingQualityHighQuality);
507     GdipSetInterpolationMode(graphics, InterpolationModeBilinear);
508     GdipSetPageScale(graphics, 10);
509     GdipSetPageUnit(graphics, UnitDocument);
510     GdipSetPixelOffsetMode(graphics, PixelOffsetModeHalf);
511     GdipSetSmoothingMode(graphics, SmoothingModeNone);
512     GdipSetTextContrast(graphics, 7);
513     GdipSetTextRenderingHint(graphics, TextRenderingHintClearTypeGridFit);
514
515     status = GdipEndContainer(graphics, cont1);
516     expect(Ok, status);
517
518     GdipGetCompositingMode(graphics, &compmode);
519     ok(defCompmode == compmode, "Expected Compositing Mode to be restored to %d, got %d\n", defCompmode, compmode);
520
521     GdipGetCompositingQuality(graphics, &compqual);
522     ok(defCompqual == compqual, "Expected Compositing Quality to be restored to %d, got %d\n", defCompqual, compqual);
523
524     GdipGetInterpolationMode(graphics, &interp);
525     ok(defInterp == interp, "Expected Interpolation Mode to be restored to %d, got %d\n", defInterp, interp);
526
527     GdipGetPageScale(graphics, &scale);
528     ok(fabs(defScale - scale) < 0.0001, "Expected Page Scale to be restored to %f, got %f\n", defScale, scale);
529
530     GdipGetPageUnit(graphics, &unit);
531     ok(defUnit == unit, "Expected Page Unit to be restored to %d, got %d\n", defUnit, unit);
532
533     GdipGetPixelOffsetMode(graphics, &offsetmode);
534     ok(defOffsetmode == offsetmode, "Expected Pixel Offset Mode to be restored to %d, got %d\n", defOffsetmode, offsetmode);
535
536     GdipGetSmoothingMode(graphics, &smoothmode);
537     ok(defSmoothmode == smoothmode, "Expected Smoothing Mode to be restored to %d, got %d\n", defSmoothmode, smoothmode);
538
539     GdipGetTextContrast(graphics, &contrast);
540     ok(defContrast == contrast, "Expected Text Contrast to be restored to %d, got %d\n", defContrast, contrast);
541
542     GdipGetTextRenderingHint(graphics, &texthint);
543     ok(defTexthint == texthint, "Expected Text Hint to be restored to %d, got %d\n", defTexthint, texthint);
544
545     /* test world transform */
546     status = GdipBeginContainer2(graphics, &cont1);
547     expect(Ok, status);
548
549     GdipCreateMatrix2(defTrans[0], defTrans[1], defTrans[2], defTrans[3],
550             defTrans[4], defTrans[5], &transform);
551     GdipSetWorldTransform(graphics, transform);
552     GdipDeleteMatrix(transform);
553     transform = NULL;
554
555     status = GdipBeginContainer2(graphics, &cont2);
556     expect(Ok, status);
557
558     GdipCreateMatrix2(10, 20, 30, 40, 50, 60, &transform);
559     GdipSetWorldTransform(graphics, transform);
560     GdipDeleteMatrix(transform);
561     transform = NULL;
562
563     status = GdipEndContainer(graphics, cont2);
564     expect(Ok, status);
565
566     GdipCreateMatrix(&transform);
567     GdipGetWorldTransform(graphics, transform);
568     GdipGetMatrixElements(transform, elems);
569     ok(fabs(defTrans[0] - elems[0]) < 0.0001 &&
570             fabs(defTrans[1] - elems[1]) < 0.0001 &&
571             fabs(defTrans[2] - elems[2]) < 0.0001 &&
572             fabs(defTrans[3] - elems[3]) < 0.0001 &&
573             fabs(defTrans[4] - elems[4]) < 0.0001 &&
574             fabs(defTrans[5] - elems[5]) < 0.0001,
575             "Expected World Transform Matrix to be restored to [%f, %f, %f, %f, %f, %f], got [%f, %f, %f, %f, %f, %f]\n",
576             defTrans[0], defTrans[1], defTrans[2], defTrans[3], defTrans[4], defTrans[5],
577             elems[0], elems[1], elems[2], elems[3], elems[4], elems[5]);
578     GdipDeleteMatrix(transform);
579     transform = NULL;
580
581     status = GdipEndContainer(graphics, cont1);
582     expect(Ok, status);
583
584     /* test clipping */
585     status = GdipBeginContainer2(graphics, &cont1);
586     expect(Ok, status);
587
588     GdipSetClipRect(graphics, defClip[0], defClip[1], defClip[2], defClip[3], CombineModeReplace);
589
590     status = GdipBeginContainer2(graphics, &cont2);
591     expect(Ok, status);
592
593     GdipSetClipRect(graphics, 2, 4, 6, 8, CombineModeReplace);
594
595     status = GdipEndContainer(graphics, cont2);
596     expect(Ok, status);
597
598     GdipGetClipBounds(graphics, &clip);
599     ok(fabs(defClip[0] - clip.X) < 0.0001 &&
600             fabs(defClip[1] - clip.Y) < 0.0001 &&
601             fabs(defClip[2] - clip.Width) < 0.0001 &&
602             fabs(defClip[3] - clip.Height) < 0.0001,
603             "Expected Clipping Rectangle to be restored to [%f, %f, %f, %f], got [%f, %f, %f, %f]\n",
604             defClip[0], defClip[1], defClip[2], defClip[3],
605             clip.X, clip.Y, clip.Width, clip.Height);
606
607     status = GdipEndContainer(graphics, cont1);
608     expect(Ok, status);
609
610     /* nesting */
611     status = GdipBeginContainer2(graphics, &cont1);
612     expect(Ok, status);
613
614     status = GdipBeginContainer2(graphics, &cont2);
615     expect(Ok, status);
616
617     status = GdipBeginContainer2(graphics, &cont3);
618     expect(Ok, status);
619
620     status = GdipEndContainer(graphics, cont3);
621     expect(Ok, status);
622
623     status = GdipBeginContainer2(graphics, &cont4);
624     expect(Ok, status);
625
626     status = GdipEndContainer(graphics, cont4);
627     expect(Ok, status);
628
629     /* skip cont2 */
630     status = GdipEndContainer(graphics, cont1);
631     expect(Ok, status);
632
633     /* end an already-ended container */
634     status = GdipEndContainer(graphics, cont1);
635     expect(Ok, status);
636
637     GdipDeleteGraphics(graphics);
638     ReleaseDC(hwnd, hdc);
639 }
640
641 static void test_GdipDrawBezierI(void)
642 {
643     GpStatus status;
644     GpGraphics *graphics = NULL;
645     GpPen *pen = NULL;
646     HDC hdc = GetDC( hwnd );
647
648     /* make a graphics object and pen object */
649     ok(hdc != NULL, "Expected HDC to be initialized\n");
650
651     status = GdipCreateFromHDC(hdc, &graphics);
652     expect(Ok, status);
653     ok(graphics != NULL, "Expected graphics to be initialized\n");
654
655     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
656     expect(Ok, status);
657     ok(pen != NULL, "Expected pen to be initialized\n");
658
659     /* InvalidParameter cases: null graphics, null pen */
660     status = GdipDrawBezierI(NULL, NULL, 0, 0, 0, 0, 0, 0, 0, 0);
661     expect(InvalidParameter, status);
662
663     status = GdipDrawBezierI(graphics, NULL, 0, 0, 0, 0, 0, 0, 0, 0);
664     expect(InvalidParameter, status);
665
666     status = GdipDrawBezierI(NULL, pen, 0, 0, 0, 0, 0, 0, 0, 0);
667     expect(InvalidParameter, status);
668
669     /* successful case */
670     status = GdipDrawBezierI(graphics, pen, 0, 0, 0, 0, 0, 0, 0, 0);
671     expect(Ok, status);
672
673     GdipDeletePen(pen);
674     GdipDeleteGraphics(graphics);
675
676     ReleaseDC(hwnd, hdc);
677 }
678
679 static void test_GdipDrawCurve3(void)
680 {
681     GpStatus status;
682     GpGraphics *graphics = NULL;
683     GpPen *pen = NULL;
684     HDC hdc = GetDC( hwnd );
685     GpPointF points[3];
686
687     points[0].X = 0;
688     points[0].Y = 0;
689
690     points[1].X = 40;
691     points[1].Y = 20;
692
693     points[2].X = 10;
694     points[2].Y = 40;
695
696     /* make a graphics object and pen object */
697     ok(hdc != NULL, "Expected HDC to be initialized\n");
698
699     status = GdipCreateFromHDC(hdc, &graphics);
700     expect(Ok, status);
701     ok(graphics != NULL, "Expected graphics to be initialized\n");
702
703     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
704     expect(Ok, status);
705     ok(pen != NULL, "Expected pen to be initialized\n");
706
707     /* InvalidParameter cases: null graphics, null pen */
708     status = GdipDrawCurve3(NULL, NULL, points, 3, 0, 2, 1);
709     expect(InvalidParameter, status);
710
711     status = GdipDrawCurve3(graphics, NULL, points, 3, 0, 2, 1);
712     expect(InvalidParameter, status);
713
714     status = GdipDrawCurve3(NULL, pen, points, 3, 0, 2, 1);
715     expect(InvalidParameter, status);
716
717     /* InvalidParameter cases: invalid count */
718     status = GdipDrawCurve3(graphics, pen, points, -1, 0, 2, 1);
719     expect(InvalidParameter, status);
720
721     status = GdipDrawCurve3(graphics, pen, points, 0, 0, 2, 1);
722     expect(InvalidParameter, status);
723
724     status = GdipDrawCurve3(graphics, pen, points, 1, 0, 0, 1);
725     expect(InvalidParameter, status);
726
727     status = GdipDrawCurve3(graphics, pen, points, 3, 4, 2, 1);
728     expect(InvalidParameter, status);
729
730     /* InvalidParameter cases: invalid number of segments */
731     status = GdipDrawCurve3(graphics, pen, points, 3, 0, -1, 1);
732     expect(InvalidParameter, status);
733
734     status = GdipDrawCurve3(graphics, pen, points, 3, 1, 2, 1);
735     expect(InvalidParameter, status);
736
737     status = GdipDrawCurve3(graphics, pen, points, 2, 0, 2, 1);
738     expect(InvalidParameter, status);
739
740     /* Valid test cases */
741     status = GdipDrawCurve3(graphics, pen, points, 2, 0, 1, 1);
742     expect(Ok, status);
743
744     status = GdipDrawCurve3(graphics, pen, points, 3, 0, 2, 2);
745     expect(Ok, status);
746
747     status = GdipDrawCurve3(graphics, pen, points, 2, 0, 1, -2);
748     expect(Ok, status);
749
750     status = GdipDrawCurve3(graphics, pen, points, 3, 1, 1, 0);
751     expect(Ok, status);
752
753     GdipDeletePen(pen);
754     GdipDeleteGraphics(graphics);
755
756     ReleaseDC(hwnd, hdc);
757 }
758
759 static void test_GdipDrawCurve3I(void)
760 {
761     GpStatus status;
762     GpGraphics *graphics = NULL;
763     GpPen *pen = NULL;
764     HDC hdc = GetDC( hwnd );
765     GpPoint points[3];
766
767     points[0].X = 0;
768     points[0].Y = 0;
769
770     points[1].X = 40;
771     points[1].Y = 20;
772
773     points[2].X = 10;
774     points[2].Y = 40;
775
776     /* make a graphics object and pen object */
777     ok(hdc != NULL, "Expected HDC to be initialized\n");
778
779     status = GdipCreateFromHDC(hdc, &graphics);
780     expect(Ok, status);
781     ok(graphics != NULL, "Expected graphics to be initialized\n");
782
783     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
784     expect(Ok, status);
785     ok(pen != NULL, "Expected pen to be initialized\n");
786
787     /* InvalidParameter cases: null graphics, null pen */
788     status = GdipDrawCurve3I(NULL, NULL, points, 3, 0, 2, 1);
789     expect(InvalidParameter, status);
790
791     status = GdipDrawCurve3I(graphics, NULL, points, 3, 0, 2, 1);
792     expect(InvalidParameter, status);
793
794     status = GdipDrawCurve3I(NULL, pen, points, 3, 0, 2, 1);
795     expect(InvalidParameter, status);
796
797     /* InvalidParameter cases: invalid count */
798     status = GdipDrawCurve3I(graphics, pen, points, -1, -1, -1, 1);
799     expect(OutOfMemory, status);
800
801     status = GdipDrawCurve3I(graphics, pen, points, 0, 0, 2, 1);
802     expect(InvalidParameter, status);
803
804     status = GdipDrawCurve3I(graphics, pen, points, 1, 0, 0, 1);
805     expect(InvalidParameter, status);
806
807     status = GdipDrawCurve3I(graphics, pen, points, 3, 4, 2, 1);
808     expect(InvalidParameter, status);
809
810     /* InvalidParameter cases: invalid number of segments */
811     status = GdipDrawCurve3I(graphics, pen, points, 3, 0, -1, 1);
812     expect(InvalidParameter, status);
813
814     status = GdipDrawCurve3I(graphics, pen, points, 3, 1, 2, 1);
815     expect(InvalidParameter, status);
816
817     status = GdipDrawCurve3I(graphics, pen, points, 2, 0, 2, 1);
818     expect(InvalidParameter, status);
819
820     /* Valid test cases */
821     status = GdipDrawCurve3I(graphics, pen, points, 2, 0, 1, 1);
822     expect(Ok, status);
823
824     status = GdipDrawCurve3I(graphics, pen, points, 3, 0, 2, 2);
825     expect(Ok, status);
826
827     status = GdipDrawCurve3I(graphics, pen, points, 2, 0, 1, -2);
828     expect(Ok, status);
829
830     status = GdipDrawCurve3I(graphics, pen, points, 3, 1, 1, 0);
831     expect(Ok, status);
832
833     GdipDeletePen(pen);
834     GdipDeleteGraphics(graphics);
835
836     ReleaseDC(hwnd, hdc);
837 }
838
839 static void test_GdipDrawCurve2(void)
840 {
841     GpStatus status;
842     GpGraphics *graphics = NULL;
843     GpPen *pen = NULL;
844     HDC hdc = GetDC( hwnd );
845     GpPointF points[3];
846
847     points[0].X = 0;
848     points[0].Y = 0;
849
850     points[1].X = 40;
851     points[1].Y = 20;
852
853     points[2].X = 10;
854     points[2].Y = 40;
855
856     /* make a graphics object and pen object */
857     ok(hdc != NULL, "Expected HDC to be initialized\n");
858
859     status = GdipCreateFromHDC(hdc, &graphics);
860     expect(Ok, status);
861     ok(graphics != NULL, "Expected graphics to be initialized\n");
862
863     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
864     expect(Ok, status);
865     ok(pen != NULL, "Expected pen to be initialized\n");
866
867     /* InvalidParameter cases: null graphics, null pen */
868     status = GdipDrawCurve2(NULL, NULL, points, 3, 1);
869     expect(InvalidParameter, status);
870
871     status = GdipDrawCurve2(graphics, NULL, points, 3, 1);
872     expect(InvalidParameter, status);
873
874     status = GdipDrawCurve2(NULL, pen, points, 3, 1);
875     expect(InvalidParameter, status);
876
877     /* InvalidParameter cases: invalid count */
878     status = GdipDrawCurve2(graphics, pen, points, -1, 1);
879     expect(InvalidParameter, status);
880
881     status = GdipDrawCurve2(graphics, pen, points, 0, 1);
882     expect(InvalidParameter, status);
883
884     status = GdipDrawCurve2(graphics, pen, points, 1, 1);
885     expect(InvalidParameter, status);
886
887     /* Valid test cases */
888     status = GdipDrawCurve2(graphics, pen, points, 2, 1);
889     expect(Ok, status);
890
891     status = GdipDrawCurve2(graphics, pen, points, 3, 2);
892     expect(Ok, status);
893
894     status = GdipDrawCurve2(graphics, pen, points, 3, -2);
895     expect(Ok, status);
896
897     status = GdipDrawCurve2(graphics, pen, points, 3, 0);
898     expect(Ok, status);
899
900     GdipDeletePen(pen);
901     GdipDeleteGraphics(graphics);
902
903     ReleaseDC(hwnd, hdc);
904 }
905
906 static void test_GdipDrawCurve2I(void)
907 {
908     GpStatus status;
909     GpGraphics *graphics = NULL;
910     GpPen *pen = NULL;
911     HDC hdc = GetDC( hwnd );
912     GpPoint points[3];
913
914     points[0].X = 0;
915     points[0].Y = 0;
916
917     points[1].X = 40;
918     points[1].Y = 20;
919
920     points[2].X = 10;
921     points[2].Y = 40;
922
923     /* make a graphics object and pen object */
924     ok(hdc != NULL, "Expected HDC to be initialized\n");
925
926     status = GdipCreateFromHDC(hdc, &graphics);
927     expect(Ok, status);
928     ok(graphics != NULL, "Expected graphics to be initialized\n");
929
930     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
931     expect(Ok, status);
932     ok(pen != NULL, "Expected pen to be initialized\n");
933
934     /* InvalidParameter cases: null graphics, null pen */
935     status = GdipDrawCurve2I(NULL, NULL, points, 3, 1);
936     expect(InvalidParameter, status);
937
938     status = GdipDrawCurve2I(graphics, NULL, points, 3, 1);
939     expect(InvalidParameter, status);
940
941     status = GdipDrawCurve2I(NULL, pen, points, 3, 1);
942     expect(InvalidParameter, status);
943
944     /* InvalidParameter cases: invalid count */
945     status = GdipDrawCurve2I(graphics, pen, points, -1, 1);
946     expect(OutOfMemory, status);
947
948     status = GdipDrawCurve2I(graphics, pen, points, 0, 1);
949     expect(InvalidParameter, status);
950
951     status = GdipDrawCurve2I(graphics, pen, points, 1, 1);
952     expect(InvalidParameter, status);
953
954     /* Valid test cases */
955     status = GdipDrawCurve2I(graphics, pen, points, 2, 1);
956     expect(Ok, status);
957
958     status = GdipDrawCurve2I(graphics, pen, points, 3, 2);
959     expect(Ok, status);
960
961     status = GdipDrawCurve2I(graphics, pen, points, 3, -2);
962     expect(Ok, status);
963
964     status = GdipDrawCurve2I(graphics, pen, points, 3, 0);
965     expect(Ok, status);
966
967     GdipDeletePen(pen);
968     GdipDeleteGraphics(graphics);
969
970     ReleaseDC(hwnd, hdc);
971 }
972
973 static void test_GdipDrawCurve(void)
974 {
975     GpStatus status;
976     GpGraphics *graphics = NULL;
977     GpPen *pen = NULL;
978     HDC hdc = GetDC( hwnd );
979     GpPointF points[3];
980
981     points[0].X = 0;
982     points[0].Y = 0;
983
984     points[1].X = 40;
985     points[1].Y = 20;
986
987     points[2].X = 10;
988     points[2].Y = 40;
989
990     /* make a graphics object and pen object */
991     ok(hdc != NULL, "Expected HDC to be initialized\n");
992
993     status = GdipCreateFromHDC(hdc, &graphics);
994     expect(Ok, status);
995     ok(graphics != NULL, "Expected graphics to be initialized\n");
996
997     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
998     expect(Ok, status);
999     ok(pen != NULL, "Expected pen to be initialized\n");
1000
1001     /* InvalidParameter cases: null graphics, null pen */
1002     status = GdipDrawCurve(NULL, NULL, points, 3);
1003     expect(InvalidParameter, status);
1004
1005     status = GdipDrawCurve(graphics, NULL, points, 3);
1006     expect(InvalidParameter, status);
1007
1008     status = GdipDrawCurve(NULL, pen, points, 3);
1009     expect(InvalidParameter, status);
1010
1011     /* InvalidParameter cases: invalid count */
1012     status = GdipDrawCurve(graphics, pen, points, -1);
1013     expect(InvalidParameter, status);
1014
1015     status = GdipDrawCurve(graphics, pen, points, 0);
1016     expect(InvalidParameter, status);
1017
1018     status = GdipDrawCurve(graphics, pen, points, 1);
1019     expect(InvalidParameter, status);
1020
1021     /* Valid test cases */
1022     status = GdipDrawCurve(graphics, pen, points, 2);
1023     expect(Ok, status);
1024
1025     status = GdipDrawCurve(graphics, pen, points, 3);
1026     expect(Ok, status);
1027
1028     GdipDeletePen(pen);
1029     GdipDeleteGraphics(graphics);
1030
1031     ReleaseDC(hwnd, hdc);
1032 }
1033
1034 static void test_GdipDrawCurveI(void)
1035 {
1036     GpStatus status;
1037     GpGraphics *graphics = NULL;
1038     GpPen *pen = NULL;
1039     HDC hdc = GetDC( hwnd );
1040     GpPoint points[3];
1041
1042     points[0].X = 0;
1043     points[0].Y = 0;
1044
1045     points[1].X = 40;
1046     points[1].Y = 20;
1047
1048     points[2].X = 10;
1049     points[2].Y = 40;
1050
1051     /* make a graphics object and pen object */
1052     ok(hdc != NULL, "Expected HDC to be initialized\n");
1053
1054     status = GdipCreateFromHDC(hdc, &graphics);
1055     expect(Ok, status);
1056     ok(graphics != NULL, "Expected graphics to be initialized\n");
1057
1058     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
1059     expect(Ok, status);
1060     ok(pen != NULL, "Expected pen to be initialized\n");
1061
1062     /* InvalidParameter cases: null graphics, null pen */
1063     status = GdipDrawCurveI(NULL, NULL, points, 3);
1064     expect(InvalidParameter, status);
1065
1066     status = GdipDrawCurveI(graphics, NULL, points, 3);
1067     expect(InvalidParameter, status);
1068
1069     status = GdipDrawCurveI(NULL, pen, points, 3);
1070     expect(InvalidParameter, status);
1071
1072     /* InvalidParameter cases: invalid count */
1073     status = GdipDrawCurveI(graphics, pen, points, -1);
1074     expect(OutOfMemory, status);
1075
1076     status = GdipDrawCurveI(graphics, pen, points, 0);
1077     expect(InvalidParameter, status);
1078
1079     status = GdipDrawCurveI(graphics, pen, points, 1);
1080     expect(InvalidParameter, status);
1081
1082     /* Valid test cases */
1083     status = GdipDrawCurveI(graphics, pen, points, 2);
1084     expect(Ok, status);
1085
1086     status = GdipDrawCurveI(graphics, pen, points, 3);
1087     expect(Ok, status);
1088
1089     GdipDeletePen(pen);
1090     GdipDeleteGraphics(graphics);
1091
1092     ReleaseDC(hwnd, hdc);
1093 }
1094
1095 static void test_GdipDrawLineI(void)
1096 {
1097     GpStatus status;
1098     GpGraphics *graphics = NULL;
1099     GpPen *pen = NULL;
1100     HDC hdc = GetDC( hwnd );
1101
1102     /* make a graphics object and pen object */
1103     ok(hdc != NULL, "Expected HDC to be initialized\n");
1104
1105     status = GdipCreateFromHDC(hdc, &graphics);
1106     expect(Ok, status);
1107     ok(graphics != NULL, "Expected graphics to be initialized\n");
1108
1109     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
1110     expect(Ok, status);
1111     ok(pen != NULL, "Expected pen to be initialized\n");
1112
1113     /* InvalidParameter cases: null graphics, null pen */
1114     status = GdipDrawLineI(NULL, NULL, 0, 0, 0, 0);
1115     expect(InvalidParameter, status);
1116
1117     status = GdipDrawLineI(graphics, NULL, 0, 0, 0, 0);
1118     expect(InvalidParameter, status);
1119
1120     status = GdipDrawLineI(NULL, pen, 0, 0, 0, 0);
1121     expect(InvalidParameter, status);
1122
1123     /* successful case */
1124     status = GdipDrawLineI(graphics, pen, 0, 0, 0, 0);
1125     expect(Ok, status);
1126
1127     GdipDeletePen(pen);
1128     GdipDeleteGraphics(graphics);
1129
1130     ReleaseDC(hwnd, hdc);
1131 }
1132
1133 static void test_GdipDrawImagePointsRect(void)
1134 {
1135     GpStatus status;
1136     GpGraphics *graphics = NULL;
1137     GpPointF ptf[4];
1138     GpBitmap *bm = NULL;
1139     BYTE rbmi[sizeof(BITMAPINFOHEADER)];
1140     BYTE buff[400];
1141     BITMAPINFO *bmi = (BITMAPINFO*)rbmi;
1142     HDC hdc = GetDC( hwnd );
1143     if (!hdc)
1144         return;
1145
1146     memset(rbmi, 0, sizeof(rbmi));
1147     bmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
1148     bmi->bmiHeader.biWidth = 10;
1149     bmi->bmiHeader.biHeight = 10;
1150     bmi->bmiHeader.biPlanes = 1;
1151     bmi->bmiHeader.biBitCount = 32;
1152     bmi->bmiHeader.biCompression = BI_RGB;
1153     status = GdipCreateBitmapFromGdiDib(bmi, buff, &bm);
1154     expect(Ok, status);
1155     ok(NULL != bm, "Expected bitmap to be initialized\n");
1156     status = GdipCreateFromHDC(hdc, &graphics);
1157     expect(Ok, status);
1158     ptf[0].X = 0;
1159     ptf[0].Y = 0;
1160     ptf[1].X = 10;
1161     ptf[1].Y = 0;
1162     ptf[2].X = 0;
1163     ptf[2].Y = 10;
1164     ptf[3].X = 10;
1165     ptf[3].Y = 10;
1166     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, ptf, 4, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1167     expect(NotImplemented, status);
1168     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, ptf, 2, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1169     expect(InvalidParameter, status);
1170     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, ptf, 3, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1171     expect(Ok, status);
1172     status = GdipDrawImagePointsRect(graphics, NULL, ptf, 3, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1173     expect(InvalidParameter, status);
1174     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, NULL, 3, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1175     expect(InvalidParameter, status);
1176     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, ptf, 3, 0, 0, 0, 0, UnitPixel, NULL, NULL, NULL);
1177     expect(Ok, status);
1178     memset(ptf, 0, sizeof(ptf));
1179     status = GdipDrawImagePointsRect(graphics, (GpImage*)bm, ptf, 3, 0, 0, 10, 10, UnitPixel, NULL, NULL, NULL);
1180     expect(Ok, status);
1181
1182     GdipDisposeImage((GpImage*)bm);
1183     GdipDeleteGraphics(graphics);
1184     ReleaseDC(hwnd, hdc);
1185 }
1186
1187 static void test_GdipDrawLinesI(void)
1188 {
1189     GpStatus status;
1190     GpGraphics *graphics = NULL;
1191     GpPen *pen = NULL;
1192     GpPoint *ptf = NULL;
1193     HDC hdc = GetDC( hwnd );
1194
1195     /* make a graphics object and pen object */
1196     ok(hdc != NULL, "Expected HDC to be initialized\n");
1197
1198     status = GdipCreateFromHDC(hdc, &graphics);
1199     expect(Ok, status);
1200     ok(graphics != NULL, "Expected graphics to be initialized\n");
1201
1202     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
1203     expect(Ok, status);
1204     ok(pen != NULL, "Expected pen to be initialized\n");
1205
1206     /* make some arbitrary valid points*/
1207     ptf = GdipAlloc(2 * sizeof(GpPointF));
1208
1209     ptf[0].X = 1;
1210     ptf[0].Y = 1;
1211
1212     ptf[1].X = 2;
1213     ptf[1].Y = 2;
1214
1215     /* InvalidParameter cases: null graphics, null pen, null points, count < 2*/
1216     status = GdipDrawLinesI(NULL, NULL, NULL, 0);
1217     expect(InvalidParameter, status);
1218
1219     status = GdipDrawLinesI(graphics, pen, ptf, 0);
1220     expect(InvalidParameter, status);
1221
1222     status = GdipDrawLinesI(graphics, NULL, ptf, 2);
1223     expect(InvalidParameter, status);
1224
1225     status = GdipDrawLinesI(NULL, pen, ptf, 2);
1226     expect(InvalidParameter, status);
1227
1228     /* successful case */
1229     status = GdipDrawLinesI(graphics, pen, ptf, 2);
1230     expect(Ok, status);
1231
1232     GdipFree(ptf);
1233     GdipDeletePen(pen);
1234     GdipDeleteGraphics(graphics);
1235
1236     ReleaseDC(hwnd, hdc);
1237 }
1238
1239 static void test_GdipFillClosedCurve(void)
1240 {
1241     GpStatus status;
1242     GpGraphics *graphics = NULL;
1243     GpSolidFill *brush = NULL;
1244     HDC hdc = GetDC( hwnd );
1245     GpPointF points[3];
1246
1247     points[0].X = 0;
1248     points[0].Y = 0;
1249
1250     points[1].X = 40;
1251     points[1].Y = 20;
1252
1253     points[2].X = 10;
1254     points[2].Y = 40;
1255
1256     /* make a graphics object and brush object */
1257     ok(hdc != NULL, "Expected HDC to be initialized\n");
1258
1259     status = GdipCreateFromHDC(hdc, &graphics);
1260     expect(Ok, status);
1261     ok(graphics != NULL, "Expected graphics to be initialized\n");
1262
1263     GdipCreateSolidFill((ARGB)0xdeadbeef, &brush);
1264
1265     /* InvalidParameter cases: null graphics, null brush, null points */
1266     status = GdipFillClosedCurve(NULL, NULL, NULL, 3);
1267     expect(InvalidParameter, status);
1268
1269     status = GdipFillClosedCurve(graphics, NULL, NULL, 3);
1270     expect(InvalidParameter, status);
1271
1272     status = GdipFillClosedCurve(NULL, (GpBrush*)brush, NULL, 3);
1273     expect(InvalidParameter, status);
1274
1275     status = GdipFillClosedCurve(NULL, NULL, points, 3);
1276     expect(InvalidParameter, status);
1277
1278     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, NULL, 3);
1279     expect(InvalidParameter, status);
1280
1281     status = GdipFillClosedCurve(graphics, NULL, points, 3);
1282     expect(InvalidParameter, status);
1283
1284     status = GdipFillClosedCurve(NULL, (GpBrush*)brush, points, 3);
1285     expect(InvalidParameter, status);
1286
1287     /* InvalidParameter cases: invalid count */
1288     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, points, -1);
1289     expect(InvalidParameter, status);
1290
1291     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, points, 0);
1292     expect(InvalidParameter, status);
1293
1294     /* Valid test cases */
1295     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, points, 1);
1296     expect(Ok, status);
1297
1298     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, points, 2);
1299     expect(Ok, status);
1300
1301     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, points, 3);
1302     expect(Ok, status);
1303
1304     GdipDeleteGraphics(graphics);
1305     GdipDeleteBrush((GpBrush*)brush);
1306
1307     ReleaseDC(hwnd, hdc);
1308 }
1309
1310 static void test_GdipFillClosedCurveI(void)
1311 {
1312     GpStatus status;
1313     GpGraphics *graphics = NULL;
1314     GpSolidFill *brush = NULL;
1315     HDC hdc = GetDC( hwnd );
1316     GpPoint points[3];
1317
1318     points[0].X = 0;
1319     points[0].Y = 0;
1320
1321     points[1].X = 40;
1322     points[1].Y = 20;
1323
1324     points[2].X = 10;
1325     points[2].Y = 40;
1326
1327     /* make a graphics object and brush object */
1328     ok(hdc != NULL, "Expected HDC to be initialized\n");
1329
1330     status = GdipCreateFromHDC(hdc, &graphics);
1331     expect(Ok, status);
1332     ok(graphics != NULL, "Expected graphics to be initialized\n");
1333
1334     GdipCreateSolidFill((ARGB)0xdeadbeef, &brush);
1335
1336     /* InvalidParameter cases: null graphics, null brush */
1337     /* Note: GdipFillClosedCurveI and GdipFillClosedCurve2I hang in Windows
1338              when points == NULL, so don't test this condition */
1339     status = GdipFillClosedCurveI(NULL, NULL, points, 3);
1340     expect(InvalidParameter, status);
1341
1342     status = GdipFillClosedCurveI(graphics, NULL, points, 3);
1343     expect(InvalidParameter, status);
1344
1345     status = GdipFillClosedCurveI(NULL, (GpBrush*)brush, points, 3);
1346     expect(InvalidParameter, status);
1347
1348     /* InvalidParameter cases: invalid count */
1349     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, points, 0);
1350     expect(InvalidParameter, status);
1351
1352     /* OutOfMemory cases: large (unsigned) int */
1353     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, points, -1);
1354     expect(OutOfMemory, status);
1355
1356     /* Valid test cases */
1357     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, points, 1);
1358     expect(Ok, status);
1359
1360     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, points, 2);
1361     expect(Ok, status);
1362
1363     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, points, 3);
1364     expect(Ok, status);
1365
1366     GdipDeleteGraphics(graphics);
1367     GdipDeleteBrush((GpBrush*)brush);
1368
1369     ReleaseDC(hwnd, hdc);
1370 }
1371
1372 static void test_Get_Release_DC(void)
1373 {
1374     GpStatus status;
1375     GpGraphics *graphics = NULL;
1376     GpPen *pen;
1377     GpSolidFill *brush;
1378     GpPath *path;
1379     HDC hdc = GetDC( hwnd );
1380     HDC retdc;
1381     REAL r;
1382     CompositingQuality quality;
1383     CompositingMode compmode;
1384     InterpolationMode intmode;
1385     GpMatrix *m;
1386     GpRegion *region;
1387     GpUnit unit;
1388     PixelOffsetMode offsetmode;
1389     SmoothingMode smoothmode;
1390     TextRenderingHint texthint;
1391     GpPointF ptf[5];
1392     GpPoint  pt[5];
1393     GpRectF  rectf[2];
1394     GpRect   rect[2];
1395     GpRegion *clip;
1396     INT i;
1397     BOOL res;
1398     ARGB color = 0x00000000;
1399     HRGN hrgn = CreateRectRgn(0, 0, 10, 10);
1400
1401     pt[0].X = 10;
1402     pt[0].Y = 10;
1403     pt[1].X = 20;
1404     pt[1].Y = 15;
1405     pt[2].X = 40;
1406     pt[2].Y = 80;
1407     pt[3].X = -20;
1408     pt[3].Y = 20;
1409     pt[4].X = 50;
1410     pt[4].Y = 110;
1411
1412     for(i = 0; i < 5;i++){
1413         ptf[i].X = (REAL)pt[i].X;
1414         ptf[i].Y = (REAL)pt[i].Y;
1415     }
1416
1417     rect[0].X = 0;
1418     rect[0].Y = 0;
1419     rect[0].Width  = 50;
1420     rect[0].Height = 70;
1421     rect[1].X = 0;
1422     rect[1].Y = 0;
1423     rect[1].Width  = 10;
1424     rect[1].Height = 20;
1425
1426     for(i = 0; i < 2;i++){
1427         rectf[i].X = (REAL)rect[i].X;
1428         rectf[i].Y = (REAL)rect[i].Y;
1429         rectf[i].Height = (REAL)rect[i].Height;
1430         rectf[i].Width  = (REAL)rect[i].Width;
1431     }
1432
1433     GdipCreateMatrix(&m);
1434     GdipCreateRegion(&region);
1435     GdipCreateSolidFill((ARGB)0xdeadbeef, &brush);
1436     GdipCreatePath(FillModeAlternate, &path);
1437     GdipCreateRegion(&clip);
1438
1439     status = GdipCreateFromHDC(hdc, &graphics);
1440     expect(Ok, status);
1441     ok(graphics != NULL, "Expected graphics to be initialized\n");
1442     status = GdipCreatePen1((ARGB)0xffff00ff, 10.0f, UnitPixel, &pen);
1443     expect(Ok, status);
1444
1445     /* NULL arguments */
1446     status = GdipGetDC(NULL, NULL);
1447     expect(InvalidParameter, status);
1448     status = GdipGetDC(graphics, NULL);
1449     expect(InvalidParameter, status);
1450     status = GdipGetDC(NULL, &retdc);
1451     expect(InvalidParameter, status);
1452
1453     status = GdipReleaseDC(NULL, NULL);
1454     expect(InvalidParameter, status);
1455     status = GdipReleaseDC(graphics, NULL);
1456     expect(InvalidParameter, status);
1457     status = GdipReleaseDC(NULL, (HDC)0xdeadbeef);
1458     expect(InvalidParameter, status);
1459
1460     /* Release without Get */
1461     status = GdipReleaseDC(graphics, hdc);
1462     expect(InvalidParameter, status);
1463
1464     retdc = NULL;
1465     status = GdipGetDC(graphics, &retdc);
1466     expect(Ok, status);
1467     ok(retdc == hdc, "Invalid HDC returned\n");
1468     /* call it once more */
1469     status = GdipGetDC(graphics, &retdc);
1470     expect(ObjectBusy, status);
1471
1472     /* try all Graphics calls here */
1473     status = GdipDrawArc(graphics, pen, 0.0, 0.0, 1.0, 1.0, 0.0, 0.0);
1474     expect(ObjectBusy, status);
1475     status = GdipDrawArcI(graphics, pen, 0, 0, 1, 1, 0.0, 0.0);
1476     expect(ObjectBusy, status);
1477     status = GdipDrawBezier(graphics, pen, 0.0, 10.0, 20.0, 15.0, 35.0, -10.0, 10.0, 10.0);
1478     expect(ObjectBusy, status);
1479     status = GdipDrawBezierI(graphics, pen, 0, 0, 0, 0, 0, 0, 0, 0);
1480     expect(ObjectBusy, status);
1481     status = GdipDrawBeziers(graphics, pen, ptf, 5);
1482     expect(ObjectBusy, status);
1483     status = GdipDrawBeziersI(graphics, pen, pt, 5);
1484     expect(ObjectBusy, status);
1485     status = GdipDrawClosedCurve(graphics, pen, ptf, 5);
1486     expect(ObjectBusy, status);
1487     status = GdipDrawClosedCurveI(graphics, pen, pt, 5);
1488     expect(ObjectBusy, status);
1489     status = GdipDrawClosedCurve2(graphics, pen, ptf, 5, 1.0);
1490     expect(ObjectBusy, status);
1491     status = GdipDrawClosedCurve2I(graphics, pen, pt, 5, 1.0);
1492     expect(ObjectBusy, status);
1493     status = GdipDrawCurve(graphics, pen, ptf, 5);
1494     expect(ObjectBusy, status);
1495     status = GdipDrawCurveI(graphics, pen, pt, 5);
1496     expect(ObjectBusy, status);
1497     status = GdipDrawCurve2(graphics, pen, ptf, 5, 1.0);
1498     expect(ObjectBusy, status);
1499     status = GdipDrawCurve2I(graphics, pen, pt, 5, 1.0);
1500     expect(ObjectBusy, status);
1501     status = GdipDrawEllipse(graphics, pen, 0.0, 0.0, 100.0, 50.0);
1502     expect(ObjectBusy, status);
1503     status = GdipDrawEllipseI(graphics, pen, 0, 0, 100, 50);
1504     expect(ObjectBusy, status);
1505     /* GdipDrawImage/GdipDrawImageI */
1506     /* GdipDrawImagePointsRect/GdipDrawImagePointsRectI */
1507     /* GdipDrawImageRectRect/GdipDrawImageRectRectI */
1508     /* GdipDrawImageRect/GdipDrawImageRectI */
1509     status = GdipDrawLine(graphics, pen, 0.0, 0.0, 100.0, 200.0);
1510     expect(ObjectBusy, status);
1511     status = GdipDrawLineI(graphics, pen, 0, 0, 100, 200);
1512     expect(ObjectBusy, status);
1513     status = GdipDrawLines(graphics, pen, ptf, 5);
1514     expect(ObjectBusy, status);
1515     status = GdipDrawLinesI(graphics, pen, pt, 5);
1516     expect(ObjectBusy, status);
1517     status = GdipDrawPath(graphics, pen, path);
1518     expect(ObjectBusy, status);
1519     status = GdipDrawPie(graphics, pen, 0.0, 0.0, 100.0, 100.0, 0.0, 90.0);
1520     expect(ObjectBusy, status);
1521     status = GdipDrawPieI(graphics, pen, 0, 0, 100, 100, 0.0, 90.0);
1522     expect(ObjectBusy, status);
1523     status = GdipDrawRectangle(graphics, pen, 0.0, 0.0, 100.0, 300.0);
1524     expect(ObjectBusy, status);
1525     status = GdipDrawRectangleI(graphics, pen, 0, 0, 100, 300);
1526     expect(ObjectBusy, status);
1527     status = GdipDrawRectangles(graphics, pen, rectf, 2);
1528     expect(ObjectBusy, status);
1529     status = GdipDrawRectanglesI(graphics, pen, rect, 2);
1530     expect(ObjectBusy, status);
1531     /* GdipDrawString */
1532     status = GdipFillClosedCurve2(graphics, (GpBrush*)brush, ptf, 5, 1.0, FillModeAlternate);
1533     expect(ObjectBusy, status);
1534     status = GdipFillClosedCurve2I(graphics, (GpBrush*)brush, pt, 5, 1.0, FillModeAlternate);
1535     expect(ObjectBusy, status);
1536     status = GdipFillClosedCurve(graphics, (GpBrush*)brush, ptf, 5);
1537     expect(ObjectBusy, status);
1538     status = GdipFillClosedCurveI(graphics, (GpBrush*)brush, pt, 5);
1539     expect(ObjectBusy, status);
1540     status = GdipFillEllipse(graphics, (GpBrush*)brush, 0.0, 0.0, 100.0, 100.0);
1541     expect(ObjectBusy, status);
1542     status = GdipFillEllipseI(graphics, (GpBrush*)brush, 0, 0, 100, 100);
1543     expect(ObjectBusy, status);
1544     status = GdipFillPath(graphics, (GpBrush*)brush, path);
1545     expect(ObjectBusy, status);
1546     status = GdipFillPie(graphics, (GpBrush*)brush, 0.0, 0.0, 100.0, 100.0, 0.0, 15.0);
1547     expect(ObjectBusy, status);
1548     status = GdipFillPieI(graphics, (GpBrush*)brush, 0, 0, 100, 100, 0.0, 15.0);
1549     expect(ObjectBusy, status);
1550     status = GdipFillPolygon(graphics, (GpBrush*)brush, ptf, 5, FillModeAlternate);
1551     expect(ObjectBusy, status);
1552     status = GdipFillPolygonI(graphics, (GpBrush*)brush, pt, 5, FillModeAlternate);
1553     expect(ObjectBusy, status);
1554     status = GdipFillPolygon2(graphics, (GpBrush*)brush, ptf, 5);
1555     expect(ObjectBusy, status);
1556     status = GdipFillPolygon2I(graphics, (GpBrush*)brush, pt, 5);
1557     expect(ObjectBusy, status);
1558     status = GdipFillRectangle(graphics, (GpBrush*)brush, 0.0, 0.0, 100.0, 100.0);
1559     expect(ObjectBusy, status);
1560     status = GdipFillRectangleI(graphics, (GpBrush*)brush, 0, 0, 100, 100);
1561     expect(ObjectBusy, status);
1562     status = GdipFillRectangles(graphics, (GpBrush*)brush, rectf, 2);
1563     expect(ObjectBusy, status);
1564     status = GdipFillRectanglesI(graphics, (GpBrush*)brush, rect, 2);
1565     expect(ObjectBusy, status);
1566     status = GdipFillRegion(graphics, (GpBrush*)brush, region);
1567     expect(ObjectBusy, status);
1568     status = GdipFlush(graphics, FlushIntentionFlush);
1569     expect(ObjectBusy, status);
1570     status = GdipGetClipBounds(graphics, rectf);
1571     expect(ObjectBusy, status);
1572     status = GdipGetClipBoundsI(graphics, rect);
1573     expect(ObjectBusy, status);
1574     status = GdipGetCompositingMode(graphics, &compmode);
1575     expect(ObjectBusy, status);
1576     status = GdipGetCompositingQuality(graphics, &quality);
1577     expect(ObjectBusy, status);
1578     status = GdipGetInterpolationMode(graphics, &intmode);
1579     expect(ObjectBusy, status);
1580     status = GdipGetNearestColor(graphics, &color);
1581     expect(ObjectBusy, status);
1582     status = GdipGetPageScale(graphics, &r);
1583     expect(ObjectBusy, status);
1584     status = GdipGetPageUnit(graphics, &unit);
1585     expect(ObjectBusy, status);
1586     status = GdipGetPixelOffsetMode(graphics, &offsetmode);
1587     expect(ObjectBusy, status);
1588     status = GdipGetSmoothingMode(graphics, &smoothmode);
1589     expect(ObjectBusy, status);
1590     status = GdipGetTextRenderingHint(graphics, &texthint);
1591     expect(ObjectBusy, status);
1592     status = GdipGetWorldTransform(graphics, m);
1593     expect(ObjectBusy, status);
1594     status = GdipGraphicsClear(graphics, 0xdeadbeef);
1595     expect(ObjectBusy, status);
1596     status = GdipIsVisiblePoint(graphics, 0.0, 0.0, &res);
1597     expect(ObjectBusy, status);
1598     status = GdipIsVisiblePointI(graphics, 0, 0, &res);
1599     expect(ObjectBusy, status);
1600     /* GdipMeasureCharacterRanges */
1601     /* GdipMeasureString */
1602     status = GdipResetClip(graphics);
1603     expect(ObjectBusy, status);
1604     status = GdipResetWorldTransform(graphics);
1605     expect(ObjectBusy, status);
1606     /* GdipRestoreGraphics */
1607     status = GdipRotateWorldTransform(graphics, 15.0, MatrixOrderPrepend);
1608     expect(ObjectBusy, status);
1609     /*  GdipSaveGraphics */
1610     status = GdipScaleWorldTransform(graphics, 1.0, 1.0, MatrixOrderPrepend);
1611     expect(ObjectBusy, status);
1612     status = GdipSetCompositingMode(graphics, CompositingModeSourceOver);
1613     expect(ObjectBusy, status);
1614     status = GdipSetCompositingQuality(graphics, CompositingQualityDefault);
1615     expect(ObjectBusy, status);
1616     status = GdipSetInterpolationMode(graphics, InterpolationModeDefault);
1617     expect(ObjectBusy, status);
1618     status = GdipSetPageScale(graphics, 1.0);
1619     expect(ObjectBusy, status);
1620     status = GdipSetPageUnit(graphics, UnitWorld);
1621     expect(ObjectBusy, status);
1622     status = GdipSetPixelOffsetMode(graphics, PixelOffsetModeDefault);
1623     expect(ObjectBusy, status);
1624     status = GdipSetSmoothingMode(graphics, SmoothingModeDefault);
1625     expect(ObjectBusy, status);
1626     status = GdipSetTextRenderingHint(graphics, TextRenderingHintSystemDefault);
1627     expect(ObjectBusy, status);
1628     status = GdipSetWorldTransform(graphics, m);
1629     expect(ObjectBusy, status);
1630     status = GdipTranslateWorldTransform(graphics, 0.0, 0.0, MatrixOrderPrepend);
1631     expect(ObjectBusy, status);
1632     status = GdipSetClipHrgn(graphics, hrgn, CombineModeReplace);
1633     expect(ObjectBusy, status);
1634     status = GdipSetClipPath(graphics, path, CombineModeReplace);
1635     expect(ObjectBusy, status);
1636     status = GdipSetClipRect(graphics, 0.0, 0.0, 10.0, 10.0, CombineModeReplace);
1637     expect(ObjectBusy, status);
1638     status = GdipSetClipRectI(graphics, 0, 0, 10, 10, CombineModeReplace);
1639     expect(ObjectBusy, status);
1640     status = GdipSetClipRegion(graphics, clip, CombineModeReplace);
1641     expect(ObjectBusy, status);
1642     status = GdipTranslateClip(graphics, 0.0, 0.0);
1643     expect(ObjectBusy, status);
1644     status = GdipTranslateClipI(graphics, 0, 0);
1645     expect(ObjectBusy, status);
1646     status = GdipDrawPolygon(graphics, pen, ptf, 5);
1647     expect(ObjectBusy, status);
1648     status = GdipDrawPolygonI(graphics, pen, pt, 5);
1649     expect(ObjectBusy, status);
1650     status = GdipGetDpiX(graphics, &r);
1651     expect(ObjectBusy, status);
1652     status = GdipGetDpiY(graphics, &r);
1653     expect(ObjectBusy, status);
1654     status = GdipMultiplyWorldTransform(graphics, m, MatrixOrderPrepend);
1655     expect(ObjectBusy, status);
1656     status = GdipGetClip(graphics, region);
1657     expect(ObjectBusy, status);
1658     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceWorld, ptf, 5);
1659     expect(ObjectBusy, status);
1660
1661     /* try to delete before release */
1662     status = GdipDeleteGraphics(graphics);
1663     expect(ObjectBusy, status);
1664
1665     status = GdipReleaseDC(graphics, retdc);
1666     expect(Ok, status);
1667
1668     GdipDeletePen(pen);
1669     GdipDeleteGraphics(graphics);
1670
1671     GdipDeleteRegion(clip);
1672     GdipDeletePath(path);
1673     GdipDeleteBrush((GpBrush*)brush);
1674     GdipDeleteRegion(region);
1675     GdipDeleteMatrix(m);
1676     DeleteObject(hrgn);
1677
1678     ReleaseDC(hwnd, hdc);
1679 }
1680
1681 static void test_transformpoints(void)
1682 {
1683     GpStatus status;
1684     GpGraphics *graphics = NULL;
1685     HDC hdc = GetDC( hwnd );
1686     GpPointF ptf[2];
1687     GpPoint pt[2];
1688
1689     status = GdipCreateFromHDC(hdc, &graphics);
1690     expect(Ok, status);
1691
1692     /* NULL arguments */
1693     status = GdipTransformPoints(NULL, CoordinateSpacePage, CoordinateSpaceWorld, NULL, 0);
1694     expect(InvalidParameter, status);
1695     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceWorld, NULL, 0);
1696     expect(InvalidParameter, status);
1697     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceWorld, ptf, 0);
1698     expect(InvalidParameter, status);
1699     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceWorld, ptf, -1);
1700     expect(InvalidParameter, status);
1701
1702     ptf[0].X = 1.0;
1703     ptf[0].Y = 0.0;
1704     ptf[1].X = 0.0;
1705     ptf[1].Y = 1.0;
1706     status = GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, ptf, 2);
1707     expect(Ok, status);
1708     expectf(1.0, ptf[0].X);
1709     expectf(0.0, ptf[0].Y);
1710     expectf(0.0, ptf[1].X);
1711     expectf(1.0, ptf[1].Y);
1712
1713     status = GdipTranslateWorldTransform(graphics, 5.0, 5.0, MatrixOrderAppend);
1714     expect(Ok, status);
1715     status = GdipSetPageUnit(graphics, UnitPixel);
1716     expect(Ok, status);
1717     status = GdipSetPageScale(graphics, 3.0);
1718     expect(Ok, status);
1719
1720     ptf[0].X = 1.0;
1721     ptf[0].Y = 0.0;
1722     ptf[1].X = 0.0;
1723     ptf[1].Y = 1.0;
1724     status = GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, ptf, 2);
1725     expect(Ok, status);
1726     expectf(18.0, ptf[0].X);
1727     expectf(15.0, ptf[0].Y);
1728     expectf(15.0, ptf[1].X);
1729     expectf(18.0, ptf[1].Y);
1730
1731     ptf[0].X = 1.0;
1732     ptf[0].Y = 0.0;
1733     ptf[1].X = 0.0;
1734     ptf[1].Y = 1.0;
1735     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceWorld, ptf, 2);
1736     expect(Ok, status);
1737     expectf(6.0, ptf[0].X);
1738     expectf(5.0, ptf[0].Y);
1739     expectf(5.0, ptf[1].X);
1740     expectf(6.0, ptf[1].Y);
1741
1742     ptf[0].X = 1.0;
1743     ptf[0].Y = 0.0;
1744     ptf[1].X = 0.0;
1745     ptf[1].Y = 1.0;
1746     status = GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpacePage, ptf, 2);
1747     expect(Ok, status);
1748     expectf(3.0, ptf[0].X);
1749     expectf(0.0, ptf[0].Y);
1750     expectf(0.0, ptf[1].X);
1751     expectf(3.0, ptf[1].Y);
1752
1753     ptf[0].X = 18.0;
1754     ptf[0].Y = 15.0;
1755     ptf[1].X = 15.0;
1756     ptf[1].Y = 18.0;
1757     status = GdipTransformPoints(graphics, CoordinateSpaceWorld, CoordinateSpaceDevice, ptf, 2);
1758     expect(Ok, status);
1759     expectf(1.0, ptf[0].X);
1760     expectf(0.0, ptf[0].Y);
1761     expectf(0.0, ptf[1].X);
1762     expectf(1.0, ptf[1].Y);
1763
1764     ptf[0].X = 6.0;
1765     ptf[0].Y = 5.0;
1766     ptf[1].X = 5.0;
1767     ptf[1].Y = 6.0;
1768     status = GdipTransformPoints(graphics, CoordinateSpaceWorld, CoordinateSpacePage, ptf, 2);
1769     expect(Ok, status);
1770     expectf(1.0, ptf[0].X);
1771     expectf(0.0, ptf[0].Y);
1772     expectf(0.0, ptf[1].X);
1773     expectf(1.0, ptf[1].Y);
1774
1775     ptf[0].X = 3.0;
1776     ptf[0].Y = 0.0;
1777     ptf[1].X = 0.0;
1778     ptf[1].Y = 3.0;
1779     status = GdipTransformPoints(graphics, CoordinateSpacePage, CoordinateSpaceDevice, ptf, 2);
1780     expect(Ok, status);
1781     expectf(1.0, ptf[0].X);
1782     expectf(0.0, ptf[0].Y);
1783     expectf(0.0, ptf[1].X);
1784     expectf(1.0, ptf[1].Y);
1785
1786     pt[0].X = 1;
1787     pt[0].Y = 0;
1788     pt[1].X = 0;
1789     pt[1].Y = 1;
1790     status = GdipTransformPointsI(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, pt, 2);
1791     expect(Ok, status);
1792     expect(18, pt[0].X);
1793     expect(15, pt[0].Y);
1794     expect(15, pt[1].X);
1795     expect(18, pt[1].Y);
1796
1797     GdipDeleteGraphics(graphics);
1798     ReleaseDC(hwnd, hdc);
1799 }
1800
1801 static void test_get_set_clip(void)
1802 {
1803     GpStatus status;
1804     GpGraphics *graphics = NULL;
1805     HDC hdc = GetDC( hwnd );
1806     GpRegion *clip;
1807     GpRectF rect;
1808     BOOL res;
1809
1810     status = GdipCreateFromHDC(hdc, &graphics);
1811     expect(Ok, status);
1812
1813     rect.X = rect.Y = 0.0;
1814     rect.Height = rect.Width = 100.0;
1815
1816     status = GdipCreateRegionRect(&rect, &clip);
1817     expect(Ok, status);
1818
1819     /* NULL arguments */
1820     status = GdipGetClip(NULL, NULL);
1821     expect(InvalidParameter, status);
1822     status = GdipGetClip(graphics, NULL);
1823     expect(InvalidParameter, status);
1824     status = GdipGetClip(NULL, clip);
1825     expect(InvalidParameter, status);
1826
1827     status = GdipSetClipRegion(NULL, NULL, CombineModeReplace);
1828     expect(InvalidParameter, status);
1829     status = GdipSetClipRegion(graphics, NULL, CombineModeReplace);
1830     expect(InvalidParameter, status);
1831
1832     status = GdipSetClipPath(NULL, NULL, CombineModeReplace);
1833     expect(InvalidParameter, status);
1834     status = GdipSetClipPath(graphics, NULL, CombineModeReplace);
1835     expect(InvalidParameter, status);
1836
1837     res = FALSE;
1838     status = GdipGetClip(graphics, clip);
1839     expect(Ok, status);
1840     status = GdipIsInfiniteRegion(clip, graphics, &res);
1841     expect(Ok, status);
1842     expect(TRUE, res);
1843
1844     /* remains infinite after reset */
1845     res = FALSE;
1846     status = GdipResetClip(graphics);
1847     expect(Ok, status);
1848     status = GdipGetClip(graphics, clip);
1849     expect(Ok, status);
1850     status = GdipIsInfiniteRegion(clip, graphics, &res);
1851     expect(Ok, status);
1852     expect(TRUE, res);
1853
1854     /* set to empty and then reset to infinite */
1855     status = GdipSetEmpty(clip);
1856     expect(Ok, status);
1857     status = GdipSetClipRegion(graphics, clip, CombineModeReplace);
1858     expect(Ok, status);
1859
1860     status = GdipGetClip(graphics, clip);
1861     expect(Ok, status);
1862     res = FALSE;
1863     status = GdipIsEmptyRegion(clip, graphics, &res);
1864     expect(Ok, status);
1865     expect(TRUE, res);
1866     status = GdipResetClip(graphics);
1867     expect(Ok, status);
1868     status = GdipGetClip(graphics, clip);
1869     expect(Ok, status);
1870     res = FALSE;
1871     status = GdipIsInfiniteRegion(clip, graphics, &res);
1872     expect(Ok, status);
1873     expect(TRUE, res);
1874
1875     GdipDeleteRegion(clip);
1876
1877     GdipDeleteGraphics(graphics);
1878     ReleaseDC(hwnd, hdc);
1879 }
1880
1881 static void test_isempty(void)
1882 {
1883     GpStatus status;
1884     GpGraphics *graphics = NULL;
1885     HDC hdc = GetDC( hwnd );
1886     GpRegion *clip;
1887     BOOL res;
1888
1889     status = GdipCreateFromHDC(hdc, &graphics);
1890     expect(Ok, status);
1891
1892     status = GdipCreateRegion(&clip);
1893     expect(Ok, status);
1894
1895     /* NULL */
1896     status = GdipIsClipEmpty(NULL, NULL);
1897     expect(InvalidParameter, status);
1898     status = GdipIsClipEmpty(graphics, NULL);
1899     expect(InvalidParameter, status);
1900     status = GdipIsClipEmpty(NULL, &res);
1901     expect(InvalidParameter, status);
1902
1903     /* default is infinite */
1904     res = TRUE;
1905     status = GdipIsClipEmpty(graphics, &res);
1906     expect(Ok, status);
1907     expect(FALSE, res);
1908
1909     GdipDeleteRegion(clip);
1910
1911     GdipDeleteGraphics(graphics);
1912     ReleaseDC(hwnd, hdc);
1913 }
1914
1915 static void test_clear(void)
1916 {
1917     GpStatus status;
1918
1919     status = GdipGraphicsClear(NULL, 0xdeadbeef);
1920     expect(InvalidParameter, status);
1921 }
1922
1923 static void test_textcontrast(void)
1924 {
1925     GpStatus status;
1926     HDC hdc = GetDC( hwnd );
1927     GpGraphics *graphics;
1928     UINT contrast;
1929
1930     status = GdipGetTextContrast(NULL, NULL);
1931     expect(InvalidParameter, status);
1932
1933     status = GdipCreateFromHDC(hdc, &graphics);
1934     expect(Ok, status);
1935
1936     status = GdipGetTextContrast(graphics, NULL);
1937     expect(InvalidParameter, status);
1938     status = GdipGetTextContrast(graphics, &contrast);
1939     expect(Ok, status);
1940     expect(4, contrast);
1941
1942     GdipDeleteGraphics(graphics);
1943     ReleaseDC(hwnd, hdc);
1944 }
1945
1946 static void test_GdipDrawString(void)
1947 {
1948     GpStatus status;
1949     GpGraphics *graphics = NULL;
1950     GpFont *fnt = NULL;
1951     RectF  rect;
1952     GpStringFormat *format;
1953     GpBrush *brush;
1954     LOGFONTA logfont;
1955     HDC hdc = GetDC( hwnd );
1956     static const WCHAR string[] = {'T','e','s','t',0};
1957     static const PointF positions[4] = {{0,0}, {1,1}, {2,2}, {3,3}};
1958     GpMatrix *matrix;
1959
1960     memset(&logfont,0,sizeof(logfont));
1961     strcpy(logfont.lfFaceName,"Arial");
1962     logfont.lfHeight = 12;
1963     logfont.lfCharSet = DEFAULT_CHARSET;
1964
1965     status = GdipCreateFromHDC(hdc, &graphics);
1966     expect(Ok, status);
1967
1968     status = GdipCreateFontFromLogfontA(hdc, &logfont, &fnt);
1969     if (status == FileNotFound)
1970     {
1971         skip("Arial not installed.\n");
1972         return;
1973     }
1974     expect(Ok, status);
1975
1976     status = GdipCreateSolidFill((ARGB)0xdeadbeef, (GpSolidFill**)&brush);
1977     expect(Ok, status);
1978
1979     status = GdipCreateStringFormat(0,0,&format);
1980     expect(Ok, status);
1981
1982     rect.X = 0;
1983     rect.Y = 0;
1984     rect.Width = 0;
1985     rect.Height = 12;
1986
1987     status = GdipDrawString(graphics, string, 4, fnt, &rect, format, brush);
1988     expect(Ok, status);
1989
1990     status = GdipCreateMatrix(&matrix);
1991     expect(Ok, status);
1992
1993     status = GdipDrawDriverString(NULL, string, 4, fnt, brush, positions, DriverStringOptionsCmapLookup, matrix);
1994     expect(InvalidParameter, status);
1995
1996     status = GdipDrawDriverString(graphics, NULL, 4, fnt, brush, positions, DriverStringOptionsCmapLookup, matrix);
1997     expect(InvalidParameter, status);
1998
1999     status = GdipDrawDriverString(graphics, string, 4, NULL, brush, positions, DriverStringOptionsCmapLookup, matrix);
2000     expect(InvalidParameter, status);
2001
2002     status = GdipDrawDriverString(graphics, string, 4, fnt, NULL, positions, DriverStringOptionsCmapLookup, matrix);
2003     expect(InvalidParameter, status);
2004
2005     status = GdipDrawDriverString(graphics, string, 4, fnt, brush, NULL, DriverStringOptionsCmapLookup, matrix);
2006     expect(InvalidParameter, status);
2007
2008     status = GdipDrawDriverString(graphics, string, 4, fnt, brush, positions, DriverStringOptionsCmapLookup|0x10, matrix);
2009     expect(Ok, status);
2010
2011     status = GdipDrawDriverString(graphics, string, 4, fnt, brush, positions, DriverStringOptionsCmapLookup, NULL);
2012     expect(Ok, status);
2013
2014     status = GdipDrawDriverString(graphics, string, 4, fnt, brush, positions, DriverStringOptionsCmapLookup, matrix);
2015     expect(Ok, status);
2016
2017     GdipDeleteMatrix(matrix);
2018     GdipDeleteGraphics(graphics);
2019     GdipDeleteBrush(brush);
2020     GdipDeleteFont(fnt);
2021     GdipDeleteStringFormat(format);
2022
2023     ReleaseDC(hwnd, hdc);
2024 }
2025
2026 static void test_GdipGetVisibleClipBounds_screen(void)
2027 {
2028     GpStatus status;
2029     GpGraphics *graphics = NULL;
2030     HDC hdc = GetDC(0);
2031     GpRectF rectf, exp, clipr;
2032     GpRect recti;
2033
2034     ok(hdc != NULL, "Expected HDC to be initialized\n");
2035
2036     status = GdipCreateFromHDC(hdc, &graphics);
2037     expect(Ok, status);
2038     ok(graphics != NULL, "Expected graphics to be initialized\n");
2039
2040     /* no clipping rect */
2041     exp.X = 0;
2042     exp.Y = 0;
2043     exp.Width = GetDeviceCaps(hdc, HORZRES);
2044     exp.Height = GetDeviceCaps(hdc, VERTRES);
2045
2046     status = GdipGetVisibleClipBounds(graphics, &rectf);
2047     expect(Ok, status);
2048     ok(rectf.X == exp.X &&
2049         rectf.Y == exp.Y &&
2050         rectf.Width == exp.Width &&
2051         rectf.Height == exp.Height,
2052         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2053         "the screen (%0.f, %0.f, %0.f, %0.f)\n",
2054         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2055         exp.X, exp.Y, exp.Width, exp.Height);
2056
2057     /* clipping rect entirely within window */
2058     exp.X = clipr.X = 10;
2059     exp.Y = clipr.Y = 12;
2060     exp.Width = clipr.Width = 14;
2061     exp.Height = clipr.Height = 16;
2062
2063     status = GdipSetClipRect(graphics, clipr.X, clipr.Y, clipr.Width, clipr.Height, CombineModeReplace);
2064     expect(Ok, status);
2065
2066     status = GdipGetVisibleClipBounds(graphics, &rectf);
2067     expect(Ok, status);
2068     ok(rectf.X == exp.X &&
2069         rectf.Y == exp.Y &&
2070         rectf.Width == exp.Width &&
2071         rectf.Height == exp.Height,
2072         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2073         "the clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2074         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2075         exp.X, exp.Y, exp.Width, exp.Height);
2076
2077     /* clipping rect partially outside of screen */
2078     clipr.X = -10;
2079     clipr.Y = -12;
2080     clipr.Width = 20;
2081     clipr.Height = 24;
2082
2083     status = GdipSetClipRect(graphics, clipr.X, clipr.Y, clipr.Width, clipr.Height, CombineModeReplace);
2084     expect(Ok, status);
2085
2086     exp.X = 0;
2087     exp.Y = 0;
2088     exp.Width = 10;
2089     exp.Height = 12;
2090
2091     status = GdipGetVisibleClipBounds(graphics, &rectf);
2092     expect(Ok, status);
2093     ok(rectf.X == exp.X &&
2094         rectf.Y == exp.Y &&
2095         rectf.Width == exp.Width &&
2096         rectf.Height == exp.Height,
2097         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2098         "the visible clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2099         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2100         exp.X, exp.Y, exp.Width, exp.Height);
2101
2102     status = GdipGetVisibleClipBoundsI(graphics, &recti);
2103     expect(Ok, status);
2104     ok(recti.X == exp.X &&
2105         recti.Y == exp.Y &&
2106         recti.Width == exp.Width &&
2107         recti.Height == exp.Height,
2108         "Expected clip bounds (%d, %d, %d, %d) to be the size of "
2109         "the visible clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2110         recti.X, recti.Y, recti.Width, recti.Height,
2111         exp.X, exp.Y, exp.Width, exp.Height);
2112
2113     GdipDeleteGraphics(graphics);
2114     ReleaseDC(0, hdc);
2115 }
2116
2117 static void test_GdipGetVisibleClipBounds_window(void)
2118 {
2119     GpStatus status;
2120     GpGraphics *graphics = NULL;
2121     GpRectF rectf, window, exp, clipr;
2122     GpRect recti;
2123     HDC hdc;
2124     PAINTSTRUCT ps;
2125     RECT wnd_rect;
2126
2127     /* get client area size */
2128     ok(GetClientRect(hwnd, &wnd_rect), "GetClientRect should have succeeded\n");
2129     window.X = wnd_rect.left;
2130     window.Y = wnd_rect.top;
2131     window.Width = wnd_rect.right - wnd_rect.left;
2132     window.Height = wnd_rect.bottom - wnd_rect.top;
2133
2134     hdc = BeginPaint(hwnd, &ps);
2135
2136     status = GdipCreateFromHDC(hdc, &graphics);
2137     expect(Ok, status);
2138     ok(graphics != NULL, "Expected graphics to be initialized\n");
2139
2140     status = GdipGetVisibleClipBounds(graphics, &rectf);
2141     expect(Ok, status);
2142     ok(rectf.X == window.X &&
2143         rectf.Y == window.Y &&
2144         rectf.Width == window.Width &&
2145         rectf.Height == window.Height,
2146         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2147         "the window (%0.f, %0.f, %0.f, %0.f)\n",
2148         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2149         window.X, window.Y, window.Width, window.Height);
2150
2151     /* clipping rect entirely within window */
2152     exp.X = clipr.X = 20;
2153     exp.Y = clipr.Y = 8;
2154     exp.Width = clipr.Width = 30;
2155     exp.Height = clipr.Height = 20;
2156
2157     status = GdipSetClipRect(graphics, clipr.X, clipr.Y, clipr.Width, clipr.Height, CombineModeReplace);
2158     expect(Ok, status);
2159
2160     status = GdipGetVisibleClipBounds(graphics, &rectf);
2161     expect(Ok, status);
2162     ok(rectf.X == exp.X &&
2163         rectf.Y == exp.Y &&
2164         rectf.Width == exp.Width &&
2165         rectf.Height == exp.Height,
2166         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2167         "the clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2168         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2169         exp.X, exp.Y, exp.Width, exp.Height);
2170
2171     /* clipping rect partially outside of window */
2172     clipr.X = window.Width - 10;
2173     clipr.Y = window.Height - 15;
2174     clipr.Width = 20;
2175     clipr.Height = 30;
2176
2177     status = GdipSetClipRect(graphics, clipr.X, clipr.Y, clipr.Width, clipr.Height, CombineModeReplace);
2178     expect(Ok, status);
2179
2180     exp.X = window.Width - 10;
2181     exp.Y = window.Height - 15;
2182     exp.Width = 10;
2183     exp.Height = 15;
2184
2185     status = GdipGetVisibleClipBounds(graphics, &rectf);
2186     expect(Ok, status);
2187     ok(rectf.X == exp.X &&
2188         rectf.Y == exp.Y &&
2189         rectf.Width == exp.Width &&
2190         rectf.Height == exp.Height,
2191         "Expected clip bounds (%0.f, %0.f, %0.f, %0.f) to be the size of "
2192         "the visible clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2193         rectf.X, rectf.Y, rectf.Width, rectf.Height,
2194         exp.X, exp.Y, exp.Width, exp.Height);
2195
2196     status = GdipGetVisibleClipBoundsI(graphics, &recti);
2197     expect(Ok, status);
2198     ok(recti.X == exp.X &&
2199         recti.Y == exp.Y &&
2200         recti.Width == exp.Width &&
2201         recti.Height == exp.Height,
2202         "Expected clip bounds (%d, %d, %d, %d) to be the size of "
2203         "the visible clipping rect (%0.f, %0.f, %0.f, %0.f)\n",
2204         recti.X, recti.Y, recti.Width, recti.Height,
2205         exp.X, exp.Y, exp.Width, exp.Height);
2206
2207     GdipDeleteGraphics(graphics);
2208     EndPaint(hwnd, &ps);
2209 }
2210
2211 static void test_GdipGetVisibleClipBounds(void)
2212 {
2213     GpGraphics* graphics = NULL;
2214     GpRectF rectf;
2215     GpRect rect;
2216     HDC hdc = GetDC( hwnd );
2217     GpStatus status;
2218
2219     status = GdipCreateFromHDC(hdc, &graphics);
2220     expect(Ok, status);
2221     ok(graphics != NULL, "Expected graphics to be initialized\n");
2222
2223     /* test null parameters */
2224     status = GdipGetVisibleClipBounds(graphics, NULL);
2225     expect(InvalidParameter, status);
2226
2227     status = GdipGetVisibleClipBounds(NULL, &rectf);
2228     expect(InvalidParameter, status);
2229
2230     status = GdipGetVisibleClipBoundsI(graphics, NULL);
2231     expect(InvalidParameter, status);
2232
2233     status = GdipGetVisibleClipBoundsI(NULL, &rect);
2234     expect(InvalidParameter, status);
2235
2236     GdipDeleteGraphics(graphics);
2237     ReleaseDC(hwnd, hdc);
2238
2239     test_GdipGetVisibleClipBounds_screen();
2240     test_GdipGetVisibleClipBounds_window();
2241 }
2242
2243 static void test_fromMemoryBitmap(void)
2244 {
2245     GpStatus status;
2246     GpGraphics *graphics = NULL;
2247     GpBitmap *bitmap = NULL;
2248     BYTE bits[48] = {0};
2249     HDC hdc=NULL;
2250     COLORREF color;
2251
2252     status = GdipCreateBitmapFromScan0(4, 4, 12, PixelFormat24bppRGB, bits, &bitmap);
2253     expect(Ok, status);
2254
2255     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2256     expect(Ok, status);
2257
2258     status = GdipGraphicsClear(graphics, 0xff686868);
2259     expect(Ok, status);
2260
2261     GdipDeleteGraphics(graphics);
2262
2263     /* drawing writes to the memory provided */
2264     expect(0x68, bits[10]);
2265
2266     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2267     expect(Ok, status);
2268
2269     status = GdipGetDC(graphics, &hdc);
2270     expect(Ok, status);
2271     ok(hdc != NULL, "got NULL hdc\n");
2272
2273     color = GetPixel(hdc, 0, 0);
2274     /* The HDC is write-only, and native fills with a solid color to figure out
2275      * which pixels have changed. */
2276     todo_wine expect(0x0c0b0d, color);
2277
2278     SetPixel(hdc, 0, 0, 0x797979);
2279     SetPixel(hdc, 1, 0, 0x0c0b0d);
2280
2281     status = GdipReleaseDC(graphics, hdc);
2282     expect(Ok, status);
2283
2284     GdipDeleteGraphics(graphics);
2285
2286     expect(0x79, bits[0]);
2287     todo_wine expect(0x68, bits[3]);
2288
2289     GdipDisposeImage((GpImage*)bitmap);
2290
2291     /* We get the same kind of write-only HDC for a "normal" bitmap */
2292     status = GdipCreateBitmapFromScan0(4, 4, 12, PixelFormat24bppRGB, NULL, &bitmap);
2293     expect(Ok, status);
2294
2295     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2296     expect(Ok, status);
2297
2298     status = GdipGetDC(graphics, &hdc);
2299     expect(Ok, status);
2300     ok(hdc != NULL, "got NULL hdc\n");
2301
2302     color = GetPixel(hdc, 0, 0);
2303     todo_wine expect(0x0c0b0d, color);
2304
2305     status = GdipReleaseDC(graphics, hdc);
2306     expect(Ok, status);
2307
2308     GdipDeleteGraphics(graphics);
2309
2310     GdipDisposeImage((GpImage*)bitmap);
2311 }
2312
2313 static void test_GdipIsVisiblePoint(void)
2314 {
2315     GpStatus status;
2316     GpGraphics *graphics = NULL;
2317     HDC hdc = GetDC( hwnd );
2318     REAL x, y;
2319     BOOL val;
2320
2321     ok(hdc != NULL, "Expected HDC to be initialized\n");
2322
2323     status = GdipCreateFromHDC(hdc, &graphics);
2324     expect(Ok, status);
2325     ok(graphics != NULL, "Expected graphics to be initialized\n");
2326
2327     /* null parameters */
2328     status = GdipIsVisiblePoint(NULL, 0, 0, &val);
2329     expect(InvalidParameter, status);
2330
2331     status = GdipIsVisiblePoint(graphics, 0, 0, NULL);
2332     expect(InvalidParameter, status);
2333
2334     status = GdipIsVisiblePointI(NULL, 0, 0, &val);
2335     expect(InvalidParameter, status);
2336
2337     status = GdipIsVisiblePointI(graphics, 0, 0, NULL);
2338     expect(InvalidParameter, status);
2339
2340     x = 0;
2341     y = 0;
2342     status = GdipIsVisiblePoint(graphics, x, y, &val);
2343     expect(Ok, status);
2344     ok(val == TRUE, "Expected (%.2f, %.2f) to be visible\n", x, y);
2345
2346     x = -10;
2347     y = 0;
2348     status = GdipIsVisiblePoint(graphics, x, y, &val);
2349     expect(Ok, status);
2350     ok(val == FALSE, "Expected (%.2f, %.2f) not to be visible\n", x, y);
2351
2352     x = 0;
2353     y = -5;
2354     status = GdipIsVisiblePoint(graphics, x, y, &val);
2355     expect(Ok, status);
2356     ok(val == FALSE, "Expected (%.2f, %.2f) not to be visible\n", x, y);
2357
2358     x = 1;
2359     y = 1;
2360     status = GdipIsVisiblePoint(graphics, x, y, &val);
2361     expect(Ok, status);
2362     ok(val == TRUE, "Expected (%.2f, %.2f) to be visible\n", x, y);
2363
2364     status = GdipSetClipRect(graphics, 10, 20, 30, 40, CombineModeReplace);
2365     expect(Ok, status);
2366
2367     x = 1;
2368     y = 1;
2369     status = GdipIsVisiblePoint(graphics, x, y, &val);
2370     expect(Ok, status);
2371     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2372
2373     x = 15.5;
2374     y = 40.5;
2375     status = GdipIsVisiblePoint(graphics, x, y, &val);
2376     expect(Ok, status);
2377     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2378
2379     /* translate into the center of the rect */
2380     GdipTranslateWorldTransform(graphics, 25, 40, MatrixOrderAppend);
2381
2382     x = 0;
2383     y = 0;
2384     status = GdipIsVisiblePoint(graphics, x, y, &val);
2385     expect(Ok, status);
2386     ok(val == TRUE, "Expected (%.2f, %.2f) to be visible\n", x, y);
2387
2388     x = 25;
2389     y = 40;
2390     status = GdipIsVisiblePoint(graphics, x, y, &val);
2391     expect(Ok, status);
2392     ok(val == FALSE, "Expected (%.2f, %.2f) not to be visible\n", x, y);
2393
2394     GdipTranslateWorldTransform(graphics, -25, -40, MatrixOrderAppend);
2395
2396     /* corner cases */
2397     x = 9;
2398     y = 19;
2399     status = GdipIsVisiblePoint(graphics, x, y, &val);
2400     expect(Ok, status);
2401     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2402
2403     x = 9.25;
2404     y = 19.25;
2405     status = GdipIsVisiblePoint(graphics, x, y, &val);
2406     expect(Ok, status);
2407     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2408
2409     x = 9.5;
2410     y = 19.5;
2411     status = GdipIsVisiblePoint(graphics, x, y, &val);
2412     expect(Ok, status);
2413     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2414
2415     x = 9.75;
2416     y = 19.75;
2417     status = GdipIsVisiblePoint(graphics, x, y, &val);
2418     expect(Ok, status);
2419     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2420
2421     x = 10;
2422     y = 20;
2423     status = GdipIsVisiblePoint(graphics, x, y, &val);
2424     expect(Ok, status);
2425     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2426
2427     x = 40;
2428     y = 20;
2429     status = GdipIsVisiblePoint(graphics, x, y, &val);
2430     expect(Ok, status);
2431     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2432
2433     x = 39;
2434     y = 59;
2435     status = GdipIsVisiblePoint(graphics, x, y, &val);
2436     expect(Ok, status);
2437     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2438
2439     x = 39.25;
2440     y = 59.25;
2441     status = GdipIsVisiblePoint(graphics, x, y, &val);
2442     expect(Ok, status);
2443     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2444
2445     x = 39.5;
2446     y = 39.5;
2447     status = GdipIsVisiblePoint(graphics, x, y, &val);
2448     expect(Ok, status);
2449     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2450
2451     x = 39.75;
2452     y = 59.75;
2453     status = GdipIsVisiblePoint(graphics, x, y, &val);
2454     expect(Ok, status);
2455     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2456
2457     x = 40;
2458     y = 60;
2459     status = GdipIsVisiblePoint(graphics, x, y, &val);
2460     expect(Ok, status);
2461     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2462
2463     x = 40.15;
2464     y = 60.15;
2465     status = GdipIsVisiblePoint(graphics, x, y, &val);
2466     expect(Ok, status);
2467     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2468
2469     x = 10;
2470     y = 60;
2471     status = GdipIsVisiblePoint(graphics, x, y, &val);
2472     expect(Ok, status);
2473     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2474
2475     /* integer version */
2476     x = 25;
2477     y = 30;
2478     status = GdipIsVisiblePointI(graphics, (INT)x, (INT)y, &val);
2479     expect(Ok, status);
2480     ok(val == TRUE, "After clipping, expected (%.2f, %.2f) to be visible\n", x, y);
2481
2482     x = 50;
2483     y = 100;
2484     status = GdipIsVisiblePointI(graphics, (INT)x, (INT)y, &val);
2485     expect(Ok, status);
2486     ok(val == FALSE, "After clipping, expected (%.2f, %.2f) not to be visible\n", x, y);
2487
2488     GdipDeleteGraphics(graphics);
2489     ReleaseDC(hwnd, hdc);
2490 }
2491
2492 static void test_GdipIsVisibleRect(void)
2493 {
2494     GpStatus status;
2495     GpGraphics *graphics = NULL;
2496     HDC hdc = GetDC( hwnd );
2497     REAL x, y, width, height;
2498     BOOL val;
2499
2500     ok(hdc != NULL, "Expected HDC to be initialized\n");
2501
2502     status = GdipCreateFromHDC(hdc, &graphics);
2503     expect(Ok, status);
2504     ok(graphics != NULL, "Expected graphics to be initialized\n");
2505
2506     status = GdipIsVisibleRect(NULL, 0, 0, 0, 0, &val);
2507     expect(InvalidParameter, status);
2508
2509     status = GdipIsVisibleRect(graphics, 0, 0, 0, 0, NULL);
2510     expect(InvalidParameter, status);
2511
2512     status = GdipIsVisibleRectI(NULL, 0, 0, 0, 0, &val);
2513     expect(InvalidParameter, status);
2514
2515     status = GdipIsVisibleRectI(graphics, 0, 0, 0, 0, NULL);
2516     expect(InvalidParameter, status);
2517
2518     /* entirely within the visible region */
2519     x = 0; width = 10;
2520     y = 0; height = 10;
2521     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2522     expect(Ok, status);
2523     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2524
2525     /* partially outside */
2526     x = -10; width = 20;
2527     y = -10; height = 20;
2528     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2529     expect(Ok, status);
2530     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2531
2532     /* entirely outside */
2533     x = -10; width = 5;
2534     y = -10; height = 5;
2535     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2536     expect(Ok, status);
2537     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2538
2539     status = GdipSetClipRect(graphics, 10, 20, 30, 40, CombineModeReplace);
2540     expect(Ok, status);
2541
2542     /* entirely within the visible region */
2543     x = 12; width = 10;
2544     y = 22; height = 10;
2545     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2546     expect(Ok, status);
2547     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2548
2549     /* partially outside */
2550     x = 35; width = 10;
2551     y = 55; height = 10;
2552     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2553     expect(Ok, status);
2554     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2555
2556     /* entirely outside */
2557     x = 45; width = 5;
2558     y = 65; height = 5;
2559     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2560     expect(Ok, status);
2561     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2562
2563     /* translate into center of clipping rect */
2564     GdipTranslateWorldTransform(graphics, 25, 40, MatrixOrderAppend);
2565
2566     x = 0; width = 10;
2567     y = 0; height = 10;
2568     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2569     expect(Ok, status);
2570     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2571
2572     x = 25; width = 5;
2573     y = 40; height = 5;
2574     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2575     expect(Ok, status);
2576     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2577
2578     GdipTranslateWorldTransform(graphics, -25, -40, MatrixOrderAppend);
2579
2580     /* corners entirely outside, but some intersections */
2581     x = 0; width = 70;
2582     y = 0; height = 90;
2583     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2584     expect(Ok, status);
2585     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2586
2587     x = 0; width = 70;
2588     y = 0; height = 30;
2589     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2590     expect(Ok, status);
2591     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2592
2593     x = 0; width = 30;
2594     y = 0; height = 90;
2595     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2596     expect(Ok, status);
2597     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2598
2599     /* edge cases */
2600     x = 0; width = 10;
2601     y = 20; height = 40;
2602     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2603     expect(Ok, status);
2604     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2605
2606     x = 10; width = 30;
2607     y = 0; height = 20;
2608     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2609     expect(Ok, status);
2610     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2611
2612     x = 40; width = 10;
2613     y = 20; height = 40;
2614     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2615     expect(Ok, status);
2616     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2617
2618     x = 10; width = 30;
2619     y = 60; height = 10;
2620     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2621     expect(Ok, status);
2622     ok(val == FALSE, "Expected (%.2f, %.2f, %.2f, %.2f) not to be visible\n", x, y, width, height);
2623
2624     /* rounding tests */
2625     x = 0.4; width = 10.4;
2626     y = 20; height = 40;
2627     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2628     expect(Ok, status);
2629     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2630
2631     x = 10; width = 30;
2632     y = 0.4; height = 20.4;
2633     status = GdipIsVisibleRect(graphics, x, y, width, height, &val);
2634     expect(Ok, status);
2635     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2636
2637     /* integer version */
2638     x = 0; width = 30;
2639     y = 0; height = 90;
2640     status = GdipIsVisibleRectI(graphics, (INT)x, (INT)y, (INT)width, (INT)height, &val);
2641     expect(Ok, status);
2642     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2643
2644     x = 12; width = 10;
2645     y = 22; height = 10;
2646     status = GdipIsVisibleRectI(graphics, (INT)x, (INT)y, (INT)width, (INT)height, &val);
2647     expect(Ok, status);
2648     ok(val == TRUE, "Expected (%.2f, %.2f, %.2f, %.2f) to be visible\n", x, y, width, height);
2649
2650     GdipDeleteGraphics(graphics);
2651     ReleaseDC(hwnd, hdc);
2652 }
2653
2654 static void test_GdipGetNearestColor(void)
2655 {
2656     GpStatus status;
2657     GpGraphics *graphics;
2658     GpBitmap *bitmap;
2659     ARGB color = 0xdeadbeef;
2660     HDC hdc = GetDC( hwnd );
2661
2662     /* create a graphics object */
2663     ok(hdc != NULL, "Expected HDC to be initialized\n");
2664
2665     status = GdipCreateFromHDC(hdc, &graphics);
2666     expect(Ok, status);
2667     ok(graphics != NULL, "Expected graphics to be initialized\n");
2668
2669     status = GdipGetNearestColor(graphics, NULL);
2670     expect(InvalidParameter, status);
2671
2672     status = GdipGetNearestColor(NULL, &color);
2673     expect(InvalidParameter, status);
2674     GdipDeleteGraphics(graphics);
2675
2676     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat1bppIndexed, NULL, &bitmap);
2677     expect(Ok, status);
2678     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2679     ok(broken(status == OutOfMemory) /* winver < Win7 */ || status == Ok, "status=%u\n", status);
2680     if (status == Ok)
2681     {
2682         status = GdipGetNearestColor(graphics, &color);
2683         expect(Ok, status);
2684         expect(0xdeadbeef, color);
2685         GdipDeleteGraphics(graphics);
2686     }
2687     GdipDisposeImage((GpImage*)bitmap);
2688
2689     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat4bppIndexed, NULL, &bitmap);
2690     expect(Ok, status);
2691     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2692     ok(broken(status == OutOfMemory) /* winver < Win7 */ || status == Ok, "status=%u\n", status);
2693     if (status == Ok)
2694     {
2695         status = GdipGetNearestColor(graphics, &color);
2696         expect(Ok, status);
2697         expect(0xdeadbeef, color);
2698         GdipDeleteGraphics(graphics);
2699     }
2700     GdipDisposeImage((GpImage*)bitmap);
2701
2702     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat8bppIndexed, NULL, &bitmap);
2703     expect(Ok, status);
2704     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2705     ok(broken(status == OutOfMemory) /* winver < Win7 */ || status == Ok, "status=%u\n", status);
2706     if (status == Ok)
2707     {
2708         status = GdipGetNearestColor(graphics, &color);
2709         expect(Ok, status);
2710         expect(0xdeadbeef, color);
2711         GdipDeleteGraphics(graphics);
2712     }
2713     GdipDisposeImage((GpImage*)bitmap);
2714
2715     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat16bppGrayScale, NULL, &bitmap);
2716     expect(Ok, status);
2717     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2718     todo_wine expect(OutOfMemory, status);
2719     if (status == Ok)
2720         GdipDeleteGraphics(graphics);
2721     GdipDisposeImage((GpImage*)bitmap);
2722
2723     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat24bppRGB, NULL, &bitmap);
2724     expect(Ok, status);
2725     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2726     expect(Ok, status);
2727     status = GdipGetNearestColor(graphics, &color);
2728     expect(Ok, status);
2729     expect(0xdeadbeef, color);
2730     GdipDeleteGraphics(graphics);
2731     GdipDisposeImage((GpImage*)bitmap);
2732
2733     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat32bppRGB, NULL, &bitmap);
2734     expect(Ok, status);
2735     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2736     expect(Ok, status);
2737     status = GdipGetNearestColor(graphics, &color);
2738     expect(Ok, status);
2739     expect(0xdeadbeef, color);
2740     GdipDeleteGraphics(graphics);
2741     GdipDisposeImage((GpImage*)bitmap);
2742
2743     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat32bppARGB, NULL, &bitmap);
2744     expect(Ok, status);
2745     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2746     expect(Ok, status);
2747     status = GdipGetNearestColor(graphics, &color);
2748     expect(Ok, status);
2749     expect(0xdeadbeef, color);
2750     GdipDeleteGraphics(graphics);
2751     GdipDisposeImage((GpImage*)bitmap);
2752
2753     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat48bppRGB, NULL, &bitmap);
2754     expect(Ok, status);
2755     if (status == Ok)
2756     {
2757         status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2758         expect(Ok, status);
2759         status = GdipGetNearestColor(graphics, &color);
2760         expect(Ok, status);
2761         expect(0xdeadbeef, color);
2762         GdipDeleteGraphics(graphics);
2763         GdipDisposeImage((GpImage*)bitmap);
2764     }
2765
2766     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat64bppARGB, NULL, &bitmap);
2767     expect(Ok, status);
2768     if (status == Ok)
2769     {
2770         status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2771         expect(Ok, status);
2772         status = GdipGetNearestColor(graphics, &color);
2773         expect(Ok, status);
2774         expect(0xdeadbeef, color);
2775         GdipDeleteGraphics(graphics);
2776         GdipDisposeImage((GpImage*)bitmap);
2777     }
2778
2779     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat64bppPARGB, NULL, &bitmap);
2780     expect(Ok, status);
2781     if (status == Ok)
2782     {
2783         status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2784         expect(Ok, status);
2785         status = GdipGetNearestColor(graphics, &color);
2786         expect(Ok, status);
2787         expect(0xdeadbeef, color);
2788         GdipDeleteGraphics(graphics);
2789         GdipDisposeImage((GpImage*)bitmap);
2790     }
2791
2792     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat16bppRGB565, NULL, &bitmap);
2793     expect(Ok, status);
2794     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2795     expect(Ok, status);
2796     status = GdipGetNearestColor(graphics, &color);
2797     expect(Ok, status);
2798     todo_wine expect(0xffa8bce8, color);
2799     GdipDeleteGraphics(graphics);
2800     GdipDisposeImage((GpImage*)bitmap);
2801
2802     status = GdipCreateBitmapFromScan0(10, 10, 10, PixelFormat16bppRGB555, NULL, &bitmap);
2803     expect(Ok, status);
2804     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
2805     expect(Ok, status);
2806     status = GdipGetNearestColor(graphics, &color);
2807     expect(Ok, status);
2808     todo_wine
2809     ok(color == 0xffa8b8e8 ||
2810        broken(color == 0xffa0b8e0), /* Win98/WinMe */
2811        "Expected ffa8b8e8, got %.8x\n", color);
2812     GdipDeleteGraphics(graphics);
2813     GdipDisposeImage((GpImage*)bitmap);
2814
2815     ReleaseDC(hwnd, hdc);
2816 }
2817
2818 static void test_string_functions(void)
2819 {
2820     GpStatus status;
2821     GpGraphics *graphics;
2822     GpFontFamily *family;
2823     GpFont *font;
2824     RectF rc, char_bounds, bounds;
2825     GpBrush *brush;
2826     ARGB color = 0xff000000;
2827     HDC hdc = GetDC( hwnd );
2828     const WCHAR fontname[] = {'T','a','h','o','m','a',0};
2829     const WCHAR teststring[] = {'M','M',' ','M','\n','M',0};
2830     const WCHAR teststring2[] = {'j',0};
2831     REAL char_width, char_height;
2832     INT codepointsfitted, linesfilled;
2833     GpStringFormat *format;
2834     CharacterRange ranges[3] = {{0, 1}, {1, 3}, {5, 1}};
2835     GpRegion *regions[4] = {0};
2836     BOOL region_isempty[4];
2837     int i;
2838     PointF position;
2839     GpMatrix *identity;
2840
2841     ok(hdc != NULL, "Expected HDC to be initialized\n");
2842     status = GdipCreateFromHDC(hdc, &graphics);
2843     expect(Ok, status);
2844     ok(graphics != NULL, "Expected graphics to be initialized\n");
2845
2846     status = GdipCreateFontFamilyFromName(fontname, NULL, &family);
2847     expect(Ok, status);
2848
2849     status = GdipCreateFont(family, 10.0, FontStyleRegular, UnitPixel, &font);
2850     expect(Ok, status);
2851
2852     status = GdipCreateSolidFill(color, (GpSolidFill**)&brush);
2853     expect(Ok, status);
2854
2855     status = GdipCreateStringFormat(0, LANG_NEUTRAL, &format);
2856     expect(Ok, status);
2857
2858     rc.X = 0;
2859     rc.Y = 0;
2860     rc.Width = 100.0;
2861     rc.Height = 100.0;
2862
2863     status = GdipDrawString(NULL, teststring, 6, font, &rc, NULL, brush);
2864     expect(InvalidParameter, status);
2865
2866     status = GdipDrawString(graphics, NULL, 6, font, &rc, NULL, brush);
2867     expect(InvalidParameter, status);
2868
2869     status = GdipDrawString(graphics, teststring, 6, NULL, &rc, NULL, brush);
2870     expect(InvalidParameter, status);
2871
2872     status = GdipDrawString(graphics, teststring, 6, font, NULL, NULL, brush);
2873     expect(InvalidParameter, status);
2874
2875     status = GdipDrawString(graphics, teststring, 6, font, &rc, NULL, NULL);
2876     expect(InvalidParameter, status);
2877
2878     status = GdipDrawString(graphics, teststring, 6, font, &rc, NULL, brush);
2879     expect(Ok, status);
2880
2881     status = GdipMeasureString(NULL, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2882     expect(InvalidParameter, status);
2883
2884     status = GdipMeasureString(graphics, NULL, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2885     expect(InvalidParameter, status);
2886
2887     status = GdipMeasureString(graphics, teststring, 6, NULL, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2888     expect(InvalidParameter, status);
2889
2890     status = GdipMeasureString(graphics, teststring, 6, font, NULL, NULL, &bounds, &codepointsfitted, &linesfilled);
2891     expect(InvalidParameter, status);
2892
2893     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, NULL, &codepointsfitted, &linesfilled);
2894     expect(InvalidParameter, status);
2895
2896     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, NULL, &linesfilled);
2897     expect(Ok, status);
2898
2899     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, NULL);
2900     expect(Ok, status);
2901
2902     status = GdipMeasureString(graphics, teststring, 1, font, &rc, NULL, &char_bounds, &codepointsfitted, &linesfilled);
2903     expect(Ok, status);
2904     expectf(0.0, char_bounds.X);
2905     expectf(0.0, char_bounds.Y);
2906     ok(char_bounds.Width > 0, "got %0.2f\n", bounds.Width);
2907     ok(char_bounds.Height > 0, "got %0.2f\n", bounds.Height);
2908     expect(1, codepointsfitted);
2909     expect(1, linesfilled);
2910
2911     status = GdipMeasureString(graphics, teststring, 2, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2912     expect(Ok, status);
2913     expectf(0.0, bounds.X);
2914     expectf(0.0, bounds.Y);
2915     ok(bounds.Width > char_bounds.Width, "got %0.2f, expected at least %0.2f\n", bounds.Width, char_bounds.Width);
2916     expectf(char_bounds.Height, bounds.Height);
2917     expect(2, codepointsfitted);
2918     expect(1, linesfilled);
2919     char_width = bounds.Width - char_bounds.Width;
2920
2921     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2922     expect(Ok, status);
2923     expectf(0.0, bounds.X);
2924     expectf(0.0, bounds.Y);
2925     ok(bounds.Width > char_bounds.Width + char_width * 2, "got %0.2f, expected at least %0.2f\n",
2926        bounds.Width, char_bounds.Width + char_width * 2);
2927     ok(bounds.Height > char_bounds.Height, "got %0.2f, expected at least %0.2f\n", bounds.Height, char_bounds.Height);
2928     expect(6, codepointsfitted);
2929     expect(2, linesfilled);
2930     char_height = bounds.Height - char_bounds.Height;
2931
2932     /* Cut off everything after the first space. */
2933     rc.Width = char_bounds.Width + char_width * 2.1;
2934
2935     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2936     expect(Ok, status);
2937     expectf(0.0, bounds.X);
2938     expectf(0.0, bounds.Y);
2939     expectf_(char_bounds.Width + char_width, bounds.Width, 0.01);
2940     expectf_(char_bounds.Height + char_height * 2, bounds.Height, 0.01);
2941     expect(6, codepointsfitted);
2942     expect(3, linesfilled);
2943
2944     /* Cut off everything including the first space. */
2945     rc.Width = char_bounds.Width + char_width * 1.5;
2946
2947     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2948     expect(Ok, status);
2949     expectf(0.0, bounds.X);
2950     expectf(0.0, bounds.Y);
2951     expectf_(char_bounds.Width + char_width, bounds.Width, 0.01);
2952     expectf_(char_bounds.Height + char_height * 2, bounds.Height, 0.01);
2953     expect(6, codepointsfitted);
2954     expect(3, linesfilled);
2955
2956     /* Cut off everything after the first character. */
2957     rc.Width = char_bounds.Width + char_width * 0.5;
2958
2959     status = GdipMeasureString(graphics, teststring, 6, font, &rc, NULL, &bounds, &codepointsfitted, &linesfilled);
2960     expect(Ok, status);
2961     expectf(0.0, bounds.X);
2962     expectf(0.0, bounds.Y);
2963     expectf_(char_bounds.Width, bounds.Width, 0.01);
2964     todo_wine expectf_(char_bounds.Height + char_height * 3, bounds.Height, 0.05);
2965     expect(6, codepointsfitted);
2966     todo_wine expect(4, linesfilled);
2967
2968     status = GdipSetStringFormatMeasurableCharacterRanges(format, 3, ranges);
2969     expect(Ok, status);
2970
2971     rc.Width = 100.0;
2972
2973     for (i=0; i<4; i++)
2974     {
2975         status = GdipCreateRegion(&regions[i]);
2976         expect(Ok, status);
2977     }
2978
2979     status = GdipMeasureCharacterRanges(NULL, teststring, 6, font, &rc, format, 3, regions);
2980     expect(InvalidParameter, status);
2981
2982     status = GdipMeasureCharacterRanges(graphics, NULL, 6, font, &rc, format, 3, regions);
2983     expect(InvalidParameter, status);
2984
2985     status = GdipMeasureCharacterRanges(graphics, teststring, 6, NULL, &rc, format, 3, regions);
2986     expect(InvalidParameter, status);
2987
2988     status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, NULL, format, 3, regions);
2989     expect(InvalidParameter, status);
2990
2991     if (0)
2992     {
2993         /* Crashes on Windows XP */
2994         status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, &rc, NULL, 3, regions);
2995         expect(InvalidParameter, status);
2996     }
2997
2998     status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, &rc, format, 3, NULL);
2999     expect(InvalidParameter, status);
3000
3001     status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, &rc, format, 2, regions);
3002     expect(InvalidParameter, status);
3003
3004     status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, &rc, format, 4, regions);
3005     expect(Ok, status);
3006
3007     for (i=0; i<4; i++)
3008     {
3009         status = GdipIsEmptyRegion(regions[i], graphics, &region_isempty[i]);
3010         expect(Ok, status);
3011     }
3012
3013     ok(!region_isempty[0], "region shouldn't be empty\n");
3014     ok(!region_isempty[1], "region shouldn't be empty\n");
3015     ok(!region_isempty[2], "region shouldn't be empty\n");
3016     ok(!region_isempty[3], "region shouldn't be empty\n");
3017
3018     /* Cut off everything after the first space, and the second line. */
3019     rc.Width = char_bounds.Width + char_width * 2.1;
3020     rc.Height = char_bounds.Height + char_height * 0.5;
3021
3022     status = GdipMeasureCharacterRanges(graphics, teststring, 6, font, &rc, format, 3, regions);
3023     expect(Ok, status);
3024
3025     for (i=0; i<4; i++)
3026     {
3027         status = GdipIsEmptyRegion(regions[i], graphics, &region_isempty[i]);
3028         expect(Ok, status);
3029     }
3030
3031     ok(!region_isempty[0], "region shouldn't be empty\n");
3032     ok(!region_isempty[1], "region shouldn't be empty\n");
3033     ok(region_isempty[2], "region should be empty\n");
3034     ok(!region_isempty[3], "region shouldn't be empty\n");
3035
3036     for (i=0; i<4; i++)
3037         GdipDeleteRegion(regions[i]);
3038
3039     GdipCreateMatrix(&identity);
3040
3041     position.X = 0;
3042     position.Y = 0;
3043
3044     rc.X = 0;
3045     rc.Y = 0;
3046     rc.Width = 0;
3047     rc.Height = 0;
3048     status = GdipMeasureDriverString(NULL, teststring, 6, font, &position,
3049         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3050         identity, &rc);
3051     expect(InvalidParameter, status);
3052
3053     status = GdipMeasureDriverString(graphics, NULL, 6, font, &position,
3054         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3055         identity, &rc);
3056     expect(InvalidParameter, status);
3057
3058     status = GdipMeasureDriverString(graphics, teststring, 6, NULL, &position,
3059         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3060         identity, &rc);
3061     expect(InvalidParameter, status);
3062
3063     status = GdipMeasureDriverString(graphics, teststring, 6, font, NULL,
3064         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3065         identity, &rc);
3066     expect(InvalidParameter, status);
3067
3068     status = GdipMeasureDriverString(graphics, teststring, 6, font, &position,
3069         0x100, identity, &rc);
3070     expect(Ok, status);
3071
3072     status = GdipMeasureDriverString(graphics, teststring, 6, font, &position,
3073         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3074         NULL, &rc);
3075     expect(Ok, status);
3076
3077     status = GdipMeasureDriverString(graphics, teststring, 6, font, &position,
3078         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3079         identity, NULL);
3080     expect(InvalidParameter, status);
3081
3082     rc.X = 0;
3083     rc.Y = 0;
3084     rc.Width = 0;
3085     rc.Height = 0;
3086     status = GdipMeasureDriverString(graphics, teststring, 6, font, &position,
3087         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3088         identity, &rc);
3089     expect(Ok, status);
3090
3091     expectf(0.0, rc.X);
3092     ok(rc.Y < 0.0, "unexpected Y %0.2f\n", rc.Y);
3093     ok(rc.Width > 0.0, "unexpected Width %0.2f\n", rc.Width);
3094     ok(rc.Height > 0.0, "unexpected Y %0.2f\n", rc.Y);
3095
3096     char_width = rc.Width;
3097     char_height = rc.Height;
3098
3099     rc.X = 0;
3100     rc.Y = 0;
3101     rc.Width = 0;
3102     rc.Height = 0;
3103     status = GdipMeasureDriverString(graphics, teststring, 4, font, &position,
3104         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3105         identity, &rc);
3106     expect(Ok, status);
3107
3108     expectf(0.0, rc.X);
3109     ok(rc.Y < 0.0, "unexpected Y %0.2f\n", rc.Y);
3110     ok(rc.Width < char_width, "got Width %0.2f, expecting less than %0.2f\n", rc.Width, char_width);
3111     expectf(char_height, rc.Height);
3112
3113     rc.X = 0;
3114     rc.Y = 0;
3115     rc.Width = 0;
3116     rc.Height = 0;
3117     status = GdipMeasureDriverString(graphics, teststring2, 1, font, &position,
3118         DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance,
3119         identity, &rc);
3120     expect(Ok, status);
3121
3122     expectf(rc.X, 0.0);
3123     ok(rc.Y < 0.0, "unexpected Y %0.2f\n", rc.Y);
3124     ok(rc.Width > 0, "unexpected Width %0.2f\n", rc.Width);
3125     expectf(rc.Height, char_height);
3126
3127     GdipDeleteMatrix(identity);
3128     GdipDeleteStringFormat(format);
3129     GdipDeleteBrush(brush);
3130     GdipDeleteFont(font);
3131     GdipDeleteFontFamily(family);
3132     GdipDeleteGraphics(graphics);
3133
3134     ReleaseDC(hwnd, hdc);
3135 }
3136
3137 static void test_get_set_interpolation(void)
3138 {
3139     GpGraphics *graphics;
3140     HDC hdc = GetDC( hwnd );
3141     GpStatus status;
3142     InterpolationMode mode;
3143
3144     ok(hdc != NULL, "Expected HDC to be initialized\n");
3145     status = GdipCreateFromHDC(hdc, &graphics);
3146     expect(Ok, status);
3147     ok(graphics != NULL, "Expected graphics to be initialized\n");
3148
3149     status = GdipGetInterpolationMode(NULL, &mode);
3150     expect(InvalidParameter, status);
3151
3152     if (0)
3153     {
3154         /* Crashes on Windows XP */
3155         status = GdipGetInterpolationMode(graphics, NULL);
3156         expect(InvalidParameter, status);
3157     }
3158
3159     status = GdipSetInterpolationMode(NULL, InterpolationModeNearestNeighbor);
3160     expect(InvalidParameter, status);
3161
3162     /* out of range */
3163     status = GdipSetInterpolationMode(graphics, InterpolationModeHighQualityBicubic+1);
3164     expect(InvalidParameter, status);
3165
3166     status = GdipSetInterpolationMode(graphics, InterpolationModeInvalid);
3167     expect(InvalidParameter, status);
3168
3169     status = GdipGetInterpolationMode(graphics, &mode);
3170     expect(Ok, status);
3171     expect(InterpolationModeBilinear, mode);
3172
3173     status = GdipSetInterpolationMode(graphics, InterpolationModeNearestNeighbor);
3174     expect(Ok, status);
3175
3176     status = GdipGetInterpolationMode(graphics, &mode);
3177     expect(Ok, status);
3178     expect(InterpolationModeNearestNeighbor, mode);
3179
3180     status = GdipSetInterpolationMode(graphics, InterpolationModeDefault);
3181     expect(Ok, status);
3182
3183     status = GdipGetInterpolationMode(graphics, &mode);
3184     expect(Ok, status);
3185     expect(InterpolationModeBilinear, mode);
3186
3187     status = GdipSetInterpolationMode(graphics, InterpolationModeLowQuality);
3188     expect(Ok, status);
3189
3190     status = GdipGetInterpolationMode(graphics, &mode);
3191     expect(Ok, status);
3192     expect(InterpolationModeBilinear, mode);
3193
3194     status = GdipSetInterpolationMode(graphics, InterpolationModeHighQuality);
3195     expect(Ok, status);
3196
3197     status = GdipGetInterpolationMode(graphics, &mode);
3198     expect(Ok, status);
3199     expect(InterpolationModeHighQualityBicubic, mode);
3200
3201     GdipDeleteGraphics(graphics);
3202
3203     ReleaseDC(hwnd, hdc);
3204 }
3205
3206 static void test_get_set_textrenderinghint(void)
3207 {
3208     GpGraphics *graphics;
3209     HDC hdc = GetDC( hwnd );
3210     GpStatus status;
3211     TextRenderingHint hint;
3212
3213     ok(hdc != NULL, "Expected HDC to be initialized\n");
3214     status = GdipCreateFromHDC(hdc, &graphics);
3215     expect(Ok, status);
3216     ok(graphics != NULL, "Expected graphics to be initialized\n");
3217
3218     status = GdipGetTextRenderingHint(NULL, &hint);
3219     expect(InvalidParameter, status);
3220
3221     status = GdipGetTextRenderingHint(graphics, NULL);
3222     expect(InvalidParameter, status);
3223
3224     status = GdipSetTextRenderingHint(NULL, TextRenderingHintAntiAlias);
3225     expect(InvalidParameter, status);
3226
3227     /* out of range */
3228     status = GdipSetTextRenderingHint(graphics, TextRenderingHintClearTypeGridFit+1);
3229     expect(InvalidParameter, status);
3230
3231     status = GdipGetTextRenderingHint(graphics, &hint);
3232     expect(Ok, status);
3233     expect(TextRenderingHintSystemDefault, hint);
3234
3235     status = GdipSetTextRenderingHint(graphics, TextRenderingHintSystemDefault);
3236     expect(Ok, status);
3237
3238     status = GdipGetTextRenderingHint(graphics, &hint);
3239     expect(Ok, status);
3240     expect(TextRenderingHintSystemDefault, hint);
3241
3242     status = GdipSetTextRenderingHint(graphics, TextRenderingHintAntiAliasGridFit);
3243     expect(Ok, status);
3244
3245     status = GdipGetTextRenderingHint(graphics, &hint);
3246     expect(Ok, status);
3247     expect(TextRenderingHintAntiAliasGridFit, hint);
3248
3249     GdipDeleteGraphics(graphics);
3250
3251     ReleaseDC(hwnd, hdc);
3252 }
3253
3254 static void test_getdc_scaled(void)
3255 {
3256     GpStatus status;
3257     GpGraphics *graphics = NULL;
3258     GpBitmap *bitmap = NULL;
3259     HDC hdc=NULL;
3260     HBRUSH hbrush, holdbrush;
3261     ARGB color;
3262
3263     status = GdipCreateBitmapFromScan0(10, 10, 12, PixelFormat24bppRGB, NULL, &bitmap);
3264     expect(Ok, status);
3265
3266     status = GdipGetImageGraphicsContext((GpImage*)bitmap, &graphics);
3267     expect(Ok, status);
3268
3269     status = GdipScaleWorldTransform(graphics, 2.0, 2.0, MatrixOrderPrepend);
3270     expect(Ok, status);
3271
3272     status = GdipGetDC(graphics, &hdc);
3273     expect(Ok, status);
3274     ok(hdc != NULL, "got NULL hdc\n");
3275
3276     hbrush = CreateSolidBrush(RGB(255, 0, 0));
3277
3278     holdbrush = SelectObject(hdc, hbrush);
3279
3280     Rectangle(hdc, 2, 2, 6, 6);
3281
3282     SelectObject(hdc, holdbrush);
3283
3284     DeleteObject(hbrush);
3285
3286     status = GdipReleaseDC(graphics, hdc);
3287     expect(Ok, status);
3288
3289     GdipDeleteGraphics(graphics);
3290
3291     status = GdipBitmapGetPixel(bitmap, 3, 3, &color);
3292     expect(Ok, status);
3293     expect(0xffff0000, color);
3294
3295     status = GdipBitmapGetPixel(bitmap, 8, 8, &color);
3296     expect(Ok, status);
3297     expect(0xff000000, color);
3298
3299     GdipDisposeImage((GpImage*)bitmap);
3300 }
3301
3302 START_TEST(graphics)
3303 {
3304     struct GdiplusStartupInput gdiplusStartupInput;
3305     ULONG_PTR gdiplusToken;
3306     WNDCLASSA class;
3307
3308     memset( &class, 0, sizeof(class) );
3309     class.lpszClassName = "gdiplus_test";
3310     class.style = CS_HREDRAW | CS_VREDRAW;
3311     class.lpfnWndProc = DefWindowProcA;
3312     class.hInstance = GetModuleHandleA(0);
3313     class.hIcon = LoadIcon(0, IDI_APPLICATION);
3314     class.hCursor = LoadCursor(NULL, IDC_ARROW);
3315     class.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
3316     RegisterClassA( &class );
3317     hwnd = CreateWindowA( "gdiplus_test", "graphics test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
3318                           CW_USEDEFAULT, CW_USEDEFAULT, 200, 200, 0, 0, GetModuleHandleA(0), 0 );
3319     ok(hwnd != NULL, "Expected window to be created\n");
3320
3321     gdiplusStartupInput.GdiplusVersion              = 1;
3322     gdiplusStartupInput.DebugEventCallback          = NULL;
3323     gdiplusStartupInput.SuppressBackgroundThread    = 0;
3324     gdiplusStartupInput.SuppressExternalCodecs      = 0;
3325
3326     GdiplusStartup(&gdiplusToken, &gdiplusStartupInput, NULL);
3327
3328     test_constructor_destructor();
3329     test_save_restore();
3330     test_GdipFillClosedCurve2();
3331     test_GdipFillClosedCurve2I();
3332     test_GdipDrawBezierI();
3333     test_GdipDrawArc();
3334     test_GdipDrawArcI();
3335     test_GdipDrawCurve();
3336     test_GdipDrawCurveI();
3337     test_GdipDrawCurve2();
3338     test_GdipDrawCurve2I();
3339     test_GdipDrawCurve3();
3340     test_GdipDrawCurve3I();
3341     test_GdipDrawLineI();
3342     test_GdipDrawLinesI();
3343     test_GdipDrawImagePointsRect();
3344     test_GdipFillClosedCurve();
3345     test_GdipFillClosedCurveI();
3346     test_GdipDrawString();
3347     test_GdipGetNearestColor();
3348     test_GdipGetVisibleClipBounds();
3349     test_GdipIsVisiblePoint();
3350     test_GdipIsVisibleRect();
3351     test_Get_Release_DC();
3352     test_BeginContainer2();
3353     test_transformpoints();
3354     test_get_set_clip();
3355     test_isempty();
3356     test_clear();
3357     test_textcontrast();
3358     test_fromMemoryBitmap();
3359     test_string_functions();
3360     test_get_set_interpolation();
3361     test_get_set_textrenderinghint();
3362     test_getdc_scaled();
3363
3364     GdiplusShutdown(gdiplusToken);
3365     DestroyWindow( hwnd );
3366 }