Initial commit - from Precise source
[freerdp-ubuntu-pcb-backport.git] / libfreerdp-gdi / 32bpp.c
1 /**
2  * FreeRDP: A Remote Desktop Protocol Client
3  * GDI 32bpp Internal Buffer Routines
4  *
5  * Copyright 2010-2011 Marc-Andre Moreau <marcandre.moreau@gmail.com>
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *     http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  */
19
20 #include <stdio.h>
21 #include <string.h>
22 #include <stdlib.h>
23 #include <freerdp/api.h>
24 #include <freerdp/freerdp.h>
25 #include <freerdp/gdi/gdi.h>
26 #include <freerdp/codec/color.h>
27
28 #include <freerdp/gdi/pen.h>
29 #include <freerdp/gdi/bitmap.h>
30 #include <freerdp/gdi/region.h>
31 #include <freerdp/gdi/clipping.h>
32 #include <freerdp/gdi/drawing.h>
33
34 #include <freerdp/gdi/32bpp.h>
35
36 uint32 gdi_get_color_32bpp(HGDI_DC hdc, GDI_COLOR color)
37 {
38         uint32 color32;
39         uint8 a, r, g, b;
40
41         a = 0xFF;
42         GetBGR32(r, g, b, color);
43
44         if (hdc->invert)
45         {
46                 color32 = ABGR32(a, r, g, b);
47         }
48         else
49         {
50                 color32 = ARGB32(a, r, g, b);
51         }
52
53         return color32;
54 }
55
56 int FillRect_32bpp(HGDI_DC hdc, HGDI_RECT rect, HGDI_BRUSH hbr)
57 {
58         int x, y;
59         uint32 *dstp;
60         uint32 color32;
61         int nXDest, nYDest;
62         int nWidth, nHeight;
63
64         gdi_RectToCRgn(rect, &nXDest, &nYDest, &nWidth, &nHeight);
65         
66         if (gdi_ClipCoords(hdc, &nXDest, &nYDest, &nWidth, &nHeight, NULL, NULL) == 0)
67                 return 0;
68
69         color32 = gdi_get_color_32bpp(hdc, hbr->color);
70
71         for (y = 0; y < nHeight; y++)
72         {
73                 dstp = (uint32*) gdi_get_bitmap_pointer(hdc, nXDest, nYDest + y);
74
75                 if (dstp != 0)
76                 {
77                         for (x = 0; x < nWidth; x++)
78                         {
79                                 *dstp = color32;
80                                 dstp++;
81                         }
82                 }
83         }
84
85         gdi_InvalidateRegion(hdc, nXDest, nYDest, nWidth, nHeight);
86         return 0;
87 }
88
89 static int BitBlt_BLACKNESS_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
90 {
91         if (hdcDest->alpha)
92         {
93                 int x, y;
94                 uint8* dstp;
95
96                 for (y = 0; y < nHeight; y++)
97                 {
98                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
99
100                         if (dstp != 0)
101                         {
102                                 for (x = 0; x < nWidth; x++)
103                                 {
104                                         *dstp = 0;
105                                         dstp++;
106
107                                         *dstp = 0;
108                                         dstp++;
109
110                                         *dstp = 0;
111                                         dstp++;
112
113                                         *dstp = 0xFF;
114                                         dstp++;
115                                 }
116                         }
117                 }
118         }
119         else
120         {
121                 int y;
122                 uint8* dstp;
123
124                 for (y = 0; y < nHeight; y++)
125                 {
126                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
127
128                         if (dstp != 0)
129                                 memset(dstp, 0, nWidth * hdcDest->bytesPerPixel);
130                 }
131         }
132
133         return 0;
134 }
135
136 static int BitBlt_WHITENESS_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
137 {
138         int y;
139         uint8* dstp;
140         
141         for (y = 0; y < nHeight; y++)
142         {
143                 dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
144
145                 if (dstp != 0)
146                         memset(dstp, 0xFF, nWidth * hdcDest->bytesPerPixel);
147         }
148
149         return 0;
150 }
151
152 static int BitBlt_SRCCOPY_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
153 {
154         int y;
155         uint8* srcp;
156         uint8* dstp;
157
158         if ((hdcDest->selectedObject != hdcSrc->selectedObject) ||
159             gdi_CopyOverlap(nXDest, nYDest, nWidth, nHeight, nXSrc, nYSrc) == 0)
160         {
161                 for (y = 0; y < nHeight; y++)
162                 {
163                         srcp = gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
164                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
165
166                         if (srcp != 0 && dstp != 0)
167                                 memcpy(dstp, srcp, nWidth * hdcDest->bytesPerPixel);
168                 }
169
170                 return 0;
171         }
172         
173         if (nYSrc < nYDest)
174         {
175                 /* copy down (bottom to top) */
176                 for (y = nHeight - 1; y >= 0; y--)
177                 {
178                         srcp = gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
179                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
180
181                         if (srcp != 0 && dstp != 0)
182                                 memmove(dstp, srcp, nWidth * hdcDest->bytesPerPixel);
183                 }
184         }
185         else if (nYSrc > nYDest || nXSrc > nXDest)
186         {
187                 /* copy up or left (top top bottom) */
188                 for (y = 0; y < nHeight; y++)
189                 {
190                         srcp = gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
191                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
192
193                         if (srcp != 0 && dstp != 0)
194                                 memmove(dstp, srcp, nWidth * hdcDest->bytesPerPixel);
195                 }
196         }
197         else
198         {
199                 /* copy straight right */
200                 for (y = 0; y < nHeight; y++)
201                 {
202                         srcp = gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
203                         dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
204
205                         if (srcp != 0 && dstp != 0)
206                                 memmove(dstp, srcp, nWidth * hdcDest->bytesPerPixel);
207                 }
208         }
209
210         return 0;
211 }
212
213 static int BitBlt_NOTSRCCOPY_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
214 {
215         int x, y;
216         uint32* srcp;
217         uint32* dstp;
218         
219         for (y = 0; y < nHeight; y++)
220         {
221                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
222                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
223
224                 if (dstp != 0)
225                 {
226                         for (x = 0; x < nWidth; x++)
227                         {
228                                 *dstp = ~(*srcp);
229                                 srcp++;
230                                 dstp++;
231                         }
232                 }
233         }
234
235         return 0;
236 }
237
238 static int BitBlt_DSTINVERT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
239 {
240         int x, y;
241         uint32* dstp;
242                 
243         for (y = 0; y < nHeight; y++)
244         {
245                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
246
247                 if (dstp != 0)
248                 {
249                         for (x = 0; x < nWidth; x++)
250                         {
251                                 *dstp = ~(*dstp);
252                                 dstp++;
253                         }
254                 }
255         }
256
257         return 0;
258 }
259
260 static int BitBlt_SRCERASE_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
261 {
262         int x, y;
263         uint32* srcp;
264         uint32* dstp;
265                 
266         for (y = 0; y < nHeight; y++)
267         {
268                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
269                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
270
271                 if (dstp != 0)
272                 {
273                         for (x = 0; x < nWidth; x++)
274                         {
275                                 *dstp = *srcp & ~(*dstp);
276                                 srcp++;
277                                 dstp++;
278                         }
279                 }
280         }
281
282         return 0;
283 }
284
285 static int BitBlt_NOTSRCERASE_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
286 {
287         int x, y;
288         uint32* srcp;
289         uint32* dstp;
290                 
291         for (y = 0; y < nHeight; y++)
292         {
293                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
294                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
295
296                 if (dstp != 0)
297                 {
298                         for (x = 0; x < nWidth; x++)
299                         {
300                                 *dstp = ~(*srcp) & ~(*dstp);
301                                 srcp++;
302                                 dstp++;
303                         }
304                 }
305         }
306
307         return 0;
308 }
309
310 static int BitBlt_SRCINVERT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
311 {
312         int x, y;
313         uint32* srcp;
314         uint32* dstp;
315                 
316         for (y = 0; y < nHeight; y++)
317         {
318                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
319                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
320
321                 if (dstp != 0)
322                 {
323                         for (x = 0; x < nWidth; x++)
324                         {
325                                 *dstp ^= *srcp;
326                                 srcp++;
327                                 dstp++;
328                         }
329                 }
330         }
331
332         return 0;
333 }
334
335 static int BitBlt_SRCAND_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
336 {
337         int x, y;
338         uint32* srcp;
339         uint32* dstp;
340                 
341         for (y = 0; y < nHeight; y++)
342         {
343                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
344                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
345
346                 if (dstp != 0)
347                 {
348                         for (x = 0; x < nWidth; x++)
349                         {
350                                 *dstp &= *srcp;
351                                 srcp++;
352                                 dstp++;
353                         }
354                 }
355         }
356
357         return 0;
358 }
359
360 static int BitBlt_SRCPAINT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
361 {
362         int x, y;
363         uint32* srcp;
364         uint32* dstp;
365                 
366         for (y = 0; y < nHeight; y++)
367         {
368                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
369                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
370
371                 if (dstp != 0)
372                 {
373                         for (x = 0; x < nWidth; x++)
374                         {
375                                 *dstp |= *srcp;
376                                 srcp++;
377                                 dstp++;
378                         }
379                 }
380         }
381
382         return 0;
383 }
384
385 static int BitBlt_DSPDxax_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
386 {       
387         int x, y;
388         uint8* srcp;
389         uint8* dstp;
390         uint8* patp;
391         uint32 color32;
392         HGDI_BITMAP hSrcBmp;
393
394         /* D = (S & P) | (~S & D) */
395         /* DSPDxax, used to draw glyphs */
396
397         color32 = gdi_get_color_32bpp(hdcDest, hdcDest->textColor);
398
399         hSrcBmp = (HGDI_BITMAP) hdcSrc->selectedObject;
400         srcp = hSrcBmp->data;
401
402         if (hdcSrc->bytesPerPixel != 1)
403         {
404                 printf("BitBlt_DSPDxax expects 1 bpp, unimplemented for %d\n", hdcSrc->bytesPerPixel);
405                 return 0;
406         }
407         
408         for (y = 0; y < nHeight; y++)
409         {
410                 srcp = gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
411                 dstp = gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
412
413                 if (dstp != 0)
414                 {
415                         for (x = 0; x < nWidth; x++)
416                         {
417                                 patp = (uint8*) &color32;
418
419                                 *dstp = (*srcp & *patp) | (~(*srcp) & *dstp);
420                                 dstp++;
421                                 patp++;
422
423                                 *dstp = (*srcp & *patp) | (~(*srcp) & *dstp);
424                                 dstp++;
425                                 patp++;
426
427                                 *dstp = (*srcp & *patp) | (~(*srcp) & *dstp);
428                                 dstp += 2;
429                                 srcp++;
430                         }
431                 }
432         }
433
434         return 0;
435 }
436
437 static int BitBlt_SPna_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
438 {
439         int x, y;
440         uint32* srcp;
441         uint32* dstp;
442         uint32* patp;
443         
444         for (y = 0; y < nHeight; y++)
445         {
446                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
447                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
448
449                 if (dstp != 0)
450                 {
451                         for (x = 0; x < nWidth; x++)
452                         {
453                                 patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
454                                 
455                                 *dstp = *srcp & ~(*patp);
456                                 srcp++;
457                                 dstp++;
458                         }
459                 }
460         }
461         
462         return 0;
463 }
464
465 static int BitBlt_DSna_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
466 {
467         int x, y;
468         uint32* srcp;
469         uint32* dstp;
470
471         for (y = 0; y < nHeight; y++)
472         {
473                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
474                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
475
476                 if (dstp != 0)
477                 {
478                         for (x = 0; x < nWidth; x++)
479                         {
480                                 *dstp = ~(*srcp) & (*dstp);
481                                 srcp++;
482                                 dstp++;
483                         }
484                 }
485         }
486
487         return 0;
488 }
489
490 static int BitBlt_PDxn_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
491 {
492         int x, y;
493         uint32* dstp;
494         uint32* patp;
495
496         for (y = 0; y < nHeight; y++)
497         {
498                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
499
500                 if (dstp != 0)
501                 {
502                         for (x = 0; x < nWidth; x++)
503                         {
504                                 patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
505
506                                 *dstp = *dstp ^ ~(*patp);
507                                 dstp++;
508                         }
509                 }
510         }
511
512         return 0;
513 }
514
515 static int BitBlt_MERGECOPY_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
516 {
517         int x, y;
518         uint32* srcp;
519         uint32* dstp;
520         uint32* patp;
521         
522         for (y = 0; y < nHeight; y++)
523         {
524                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
525                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
526
527                 if (dstp != 0)
528                 {
529                         for (x = 0; x < nWidth; x++)
530                         {
531                                 patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
532                                 
533                                 *dstp = *srcp & *patp;
534                                 srcp++;
535                                 dstp++;
536                         }
537                 }
538         }
539         
540         return 0;
541 }
542
543 static int BitBlt_MERGEPAINT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
544 {
545         int x, y;
546         uint32* srcp;
547         uint32* dstp;
548         
549         for (y = 0; y < nHeight; y++)
550         {
551                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
552                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
553
554                 if (dstp != 0)
555                 {
556                         for (x = 0; x < nWidth; x++)
557                         {                               
558                                 *dstp = ~(*srcp) | *dstp;
559                                 srcp++;
560                                 dstp++;
561                         }
562                 }
563         }
564         
565         return 0;
566 }
567
568 static int BitBlt_PATCOPY_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
569 {
570         int x, y;
571         uint32* dstp;
572         uint32* patp;
573         uint32 color32;
574
575         if (hdcDest->brush->style == GDI_BS_SOLID)
576         {
577                 color32 = gdi_get_color_32bpp(hdcDest, hdcDest->brush->color);
578
579                 for (y = 0; y < nHeight; y++)
580                 {
581                         dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
582
583                         if (dstp != 0)
584                         {
585                                 for (x = 0; x < nWidth; x++)
586                                 {
587                                         *dstp = color32;
588                                         dstp++;
589                                 }
590                         }
591                 }
592         }
593         else
594         {
595                 for (y = 0; y < nHeight; y++)
596                 {
597                         dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
598
599                         if (dstp != 0)
600                         {
601                                 for (x = 0; x < nWidth; x++)
602                                 {
603                                         patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
604                                         *dstp = *patp;
605                                         dstp++;
606                                 }
607                         }
608                 }
609         }
610         
611         return 0;
612 }
613
614 static int BitBlt_PATINVERT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight)
615 {
616         int x, y;
617         uint32* dstp;
618         uint32* patp;
619         uint32 color32;
620                 
621         if (hdcDest->brush->style == GDI_BS_SOLID)
622         {
623                 color32 = gdi_get_color_32bpp(hdcDest, hdcDest->brush->color);
624
625                 for (y = 0; y < nHeight; y++)
626                 {
627                         dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
628
629                         if (dstp != 0)
630                         {
631                                 for (x = 0; x < nWidth; x++)
632                                 {
633                                         *dstp ^= color32;
634                                         dstp++;
635                                 }
636                         }
637                 }
638         }
639         else
640         {
641                 for (y = 0; y < nHeight; y++)
642                 {
643                         dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
644
645                         if (dstp != 0)
646                         {
647                                 for (x = 0; x < nWidth; x++)
648                                 {
649                                         patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
650                                         *dstp = *patp ^ *dstp;
651                                         dstp++;
652                                 }
653                         }
654                 }
655         }
656         
657         return 0;
658 }
659
660 static int BitBlt_PATPAINT_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc)
661 {
662         int x, y;
663         uint32* srcp;
664         uint32* dstp;
665         uint32* patp;
666         
667         for (y = 0; y < nHeight; y++)
668         {
669                 srcp = (uint32*) gdi_get_bitmap_pointer(hdcSrc, nXSrc, nYSrc + y);
670                 dstp = (uint32*) gdi_get_bitmap_pointer(hdcDest, nXDest, nYDest + y);
671
672                 if (dstp != 0)
673                 {
674                         for (x = 0; x < nWidth; x++)
675                         {
676                                 patp = (uint32*) gdi_get_brush_pointer(hdcDest, x, y);
677                                 *dstp = *dstp | (*patp | ~(*srcp));
678                                 srcp++;
679                                 dstp++;
680                         }
681                 }
682         }
683         
684         return 0;
685 }
686
687 int BitBlt_32bpp(HGDI_DC hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, HGDI_DC hdcSrc, int nXSrc, int nYSrc, int rop)
688 {
689         if (hdcSrc != NULL)
690         {
691                 if (gdi_ClipCoords(hdcDest, &nXDest, &nYDest, &nWidth, &nHeight, &nXSrc, &nYSrc) == 0)
692                         return 0;
693         }
694         else
695         {
696                 if (gdi_ClipCoords(hdcDest, &nXDest, &nYDest, &nWidth, &nHeight, NULL, NULL) == 0)
697                         return 0;
698         }
699         
700         gdi_InvalidateRegion(hdcDest, nXDest, nYDest, nWidth, nHeight);
701         
702         switch (rop)
703         {
704                 case GDI_BLACKNESS:
705                         return BitBlt_BLACKNESS_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight);
706                         break;
707
708                 case GDI_WHITENESS:
709                         return BitBlt_WHITENESS_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight);
710                         break;
711
712                 case GDI_SRCCOPY:
713                         return BitBlt_SRCCOPY_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
714                         break;
715
716                 case GDI_SPna:
717                         return BitBlt_SPna_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
718                         break;
719
720                 case GDI_DSna:
721                         return BitBlt_DSna_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
722                         break;
723
724                 case GDI_DSPDxax:
725                         return BitBlt_DSPDxax_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
726                         break;
727                         
728                 case GDI_NOTSRCCOPY:
729                         return BitBlt_NOTSRCCOPY_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
730                         break;
731
732                 case GDI_DSTINVERT:
733                         return BitBlt_DSTINVERT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight);
734                         break;
735
736                 case GDI_SRCERASE:
737                         return BitBlt_SRCERASE_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
738                         break;
739
740                 case GDI_NOTSRCERASE:
741                         return BitBlt_NOTSRCERASE_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
742                         break;
743
744                 case GDI_SRCINVERT:
745                         return BitBlt_SRCINVERT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
746                         break;
747
748                 case GDI_SRCAND:
749                         return BitBlt_SRCAND_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
750                         break;
751
752                 case GDI_SRCPAINT:
753                         return BitBlt_SRCPAINT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
754                         break;
755
756                 case GDI_MERGECOPY:
757                         return BitBlt_MERGECOPY_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
758                         break;
759
760                 case GDI_MERGEPAINT:
761                         return BitBlt_MERGEPAINT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
762                         break;
763
764                 case GDI_PATCOPY:
765                         return BitBlt_PATCOPY_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight);
766                         break;
767
768                 case GDI_PATINVERT:
769                         return BitBlt_PATINVERT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight);
770                         break;
771
772                 case GDI_PATPAINT:
773                         return BitBlt_PATPAINT_32bpp(hdcDest, nXDest, nYDest, nWidth, nHeight, hdcSrc, nXSrc, nYSrc);
774                         break;
775         }
776         
777         printf("BitBlt: unknown rop: 0x%08X\n", rop);
778         return 1;
779 }
780
781 int PatBlt_32bpp(HGDI_DC hdc, int nXLeft, int nYLeft, int nWidth, int nHeight, int rop)
782 {
783         if (gdi_ClipCoords(hdc, &nXLeft, &nYLeft, &nWidth, &nHeight, NULL, NULL) == 0)
784                 return 0;
785         
786         gdi_InvalidateRegion(hdc, nXLeft, nYLeft, nWidth, nHeight);
787
788         switch (rop)
789         {
790                 case GDI_PATCOPY:
791                         return BitBlt_PATCOPY_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
792                         break;
793
794                 case GDI_PATINVERT:
795                         return BitBlt_PATINVERT_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
796                         break;
797                         
798                 case GDI_DSTINVERT:
799                         return BitBlt_DSTINVERT_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
800                         break;
801
802                 case GDI_BLACKNESS:
803                         return BitBlt_BLACKNESS_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
804                         break;
805
806                 case GDI_WHITENESS:
807                         return BitBlt_WHITENESS_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
808                         break;
809
810                 case GDI_PDxn:
811                         return BitBlt_PDxn_32bpp(hdc, nXLeft, nYLeft, nWidth, nHeight);
812                         break;
813
814                 default:
815                         break;
816         }
817         
818         printf("PatBlt: unknown rop: 0x%08X\n", rop);
819
820         return 1;
821 }
822
823 INLINE void SetPixel_BLACK_32bpp(uint32* pixel, uint32* pen)
824 {
825         /* D = 0 */
826         *pixel = 0;
827 }
828
829 INLINE void SetPixel_NOTMERGEPEN_32bpp(uint32* pixel, uint32* pen)
830 {
831         /* D = ~(D | P) */
832         *pixel = ~(*pixel | *pen);
833 }
834
835 INLINE void SetPixel_MASKNOTPEN_32bpp(uint32* pixel, uint32* pen)
836 {
837         /* D = D & ~P */
838         *pixel &= ~(*pen);
839 }
840
841 INLINE void SetPixel_NOTCOPYPEN_32bpp(uint32* pixel, uint32* pen)
842 {
843         /* D = ~P */
844         *pixel = ~(*pen);
845 }
846
847 INLINE void SetPixel_MASKPENNOT_32bpp(uint32* pixel, uint32* pen)
848 {
849         /* D = P & ~D */
850         *pixel = *pen & ~*pixel;
851 }
852
853 INLINE void SetPixel_NOT_32bpp(uint32* pixel, uint32* pen)
854 {
855         /* D = ~D */
856         *pixel = ~(*pixel);
857 }
858
859 INLINE void SetPixel_XORPEN_32bpp(uint32* pixel, uint32* pen)
860 {
861         /* D = D ^ P */
862         *pixel = *pixel ^ *pen;
863 }
864
865 INLINE void SetPixel_NOTMASKPEN_32bpp(uint32* pixel, uint32* pen)
866 {
867         /* D = ~(D & P) */
868         *pixel = ~(*pixel & *pen);
869 }
870
871 INLINE void SetPixel_MASKPEN_32bpp(uint32* pixel, uint32* pen)
872 {
873         /* D = D & P */
874         *pixel &= *pen;
875 }
876
877 INLINE void SetPixel_NOTXORPEN_32bpp(uint32* pixel, uint32* pen)
878 {
879         /* D = ~(D ^ P) */
880         *pixel = ~(*pixel ^ *pen);
881 }
882
883 INLINE void SetPixel_NOP_32bpp(uint32* pixel, uint32* pen)
884 {
885         /* D = D */
886 }
887
888 INLINE void SetPixel_MERGENOTPEN_32bpp(uint32* pixel, uint32* pen)
889 {
890         /* D = D | ~P */
891         *pixel |= ~(*pen);
892 }
893
894 INLINE void SetPixel_COPYPEN_32bpp(uint32* pixel, uint32* pen)
895 {
896         /* D = P */
897         *pixel = *pen;
898 }
899
900 INLINE void SetPixel_MERGEPENNOT_32bpp(uint32* pixel, uint32* pen)
901 {
902         /* D = P | ~D */
903         *pixel = *pen | ~(*pixel);
904 }
905
906 INLINE void SetPixel_MERGEPEN_32bpp(uint32* pixel, uint32* pen)
907 {
908         /* D = P | D */
909         *pixel |= *pen;
910 }
911
912 INLINE void SetPixel_WHITE_32bpp(uint32* pixel, uint32* pen)
913 {
914         /* D = 1 */
915         *pixel = 0xFFFFFF;
916 }
917
918 #define PIXEL_TYPE              uint32
919 #define GDI_GET_POINTER         gdi_GetPointer_32bpp
920 #define GDI_GET_PEN_COLOR       gdi_GetPenColor_32bpp
921
922 #define LINE_TO                 LineTo_BLACK_32bpp
923 #define SET_PIXEL_ROP2          SetPixel_BLACK_32bpp
924 #include "include/line.c"
925 #undef LINE_TO
926 #undef SET_PIXEL_ROP2
927
928 #define LINE_TO                 LineTo_NOTMERGEPEN_32bpp
929 #define SET_PIXEL_ROP2          SetPixel_NOTMERGEPEN_32bpp
930 #include "include/line.c"
931 #undef LINE_TO
932 #undef SET_PIXEL_ROP2
933
934 #define LINE_TO                 LineTo_MASKNOTPEN_32bpp
935 #define SET_PIXEL_ROP2          SetPixel_MASKNOTPEN_32bpp
936 #include "include/line.c"
937 #undef LINE_TO
938 #undef SET_PIXEL_ROP2
939
940 #define LINE_TO                 LineTo_NOTCOPYPEN_32bpp
941 #define SET_PIXEL_ROP2          SetPixel_NOTCOPYPEN_32bpp
942 #include "include/line.c"
943 #undef LINE_TO
944 #undef SET_PIXEL_ROP2
945
946 #define LINE_TO                 LineTo_MASKPENNOT_32bpp
947 #define SET_PIXEL_ROP2          SetPixel_MASKPENNOT_32bpp
948 #include "include/line.c"
949 #undef LINE_TO
950 #undef SET_PIXEL_ROP2
951
952 #define LINE_TO                 LineTo_NOT_32bpp
953 #define SET_PIXEL_ROP2          SetPixel_NOT_32bpp
954 #include "include/line.c"
955 #undef LINE_TO
956 #undef SET_PIXEL_ROP2
957
958 #define LINE_TO                 LineTo_XORPEN_32bpp
959 #define SET_PIXEL_ROP2          SetPixel_XORPEN_32bpp
960 #include "include/line.c"
961 #undef LINE_TO
962 #undef SET_PIXEL_ROP2
963
964 #define LINE_TO                 LineTo_NOTMASKPEN_32bpp
965 #define SET_PIXEL_ROP2          SetPixel_NOTMASKPEN_32bpp
966 #include "include/line.c"
967 #undef LINE_TO
968 #undef SET_PIXEL_ROP2
969
970 #define LINE_TO                 LineTo_MASKPEN_32bpp
971 #define SET_PIXEL_ROP2          SetPixel_MASKPEN_32bpp
972 #include "include/line.c"
973 #undef LINE_TO
974 #undef SET_PIXEL_ROP2
975
976 #define LINE_TO                 LineTo_NOTXORPEN_32bpp
977 #define SET_PIXEL_ROP2          SetPixel_NOTXORPEN_32bpp
978 #include "include/line.c"
979 #undef LINE_TO
980 #undef SET_PIXEL_ROP2
981
982 #define LINE_TO                 LineTo_NOP_32bpp
983 #define SET_PIXEL_ROP2          SetPixel_NOP_32bpp
984 #include "include/line.c"
985 #undef LINE_TO
986 #undef SET_PIXEL_ROP2
987
988 #define LINE_TO                 LineTo_MERGENOTPEN_32bpp
989 #define SET_PIXEL_ROP2          SetPixel_MERGENOTPEN_32bpp
990 #include "include/line.c"
991 #undef LINE_TO
992 #undef SET_PIXEL_ROP2
993
994 #define LINE_TO                 LineTo_COPYPEN_32bpp
995 #define SET_PIXEL_ROP2          SetPixel_COPYPEN_32bpp
996 #include "include/line.c"
997 #undef LINE_TO
998 #undef SET_PIXEL_ROP2
999
1000 #define LINE_TO                 LineTo_MERGEPENNOT_32bpp
1001 #define SET_PIXEL_ROP2          SetPixel_MERGEPENNOT_32bpp
1002 #include "include/line.c"
1003 #undef LINE_TO
1004 #undef SET_PIXEL_ROP2
1005
1006 #define LINE_TO                 LineTo_MERGEPEN_32bpp
1007 #define SET_PIXEL_ROP2          SetPixel_MERGEPEN_32bpp
1008 #include "include/line.c"
1009 #undef LINE_TO
1010 #undef SET_PIXEL_ROP2
1011
1012 #define LINE_TO                 LineTo_WHITE_32bpp
1013 #define SET_PIXEL_ROP2          SetPixel_WHITE_32bpp
1014 #include "include/line.c"
1015 #undef LINE_TO
1016 #undef SET_PIXEL_ROP2
1017
1018 #undef PIXEL_TYPE
1019 #undef GDI_GET_POINTER
1020 #undef GDI_GET_PEN_COLOR
1021
1022 pLineTo_32bpp LineTo_ROP2_32bpp[32] =
1023 {
1024         LineTo_BLACK_32bpp,
1025         LineTo_NOTMERGEPEN_32bpp,
1026         LineTo_MASKNOTPEN_32bpp,
1027         LineTo_NOTCOPYPEN_32bpp,
1028         LineTo_MASKPENNOT_32bpp,
1029         LineTo_NOT_32bpp,
1030         LineTo_XORPEN_32bpp,
1031         LineTo_NOTMASKPEN_32bpp,
1032         LineTo_MASKPEN_32bpp,
1033         LineTo_NOTXORPEN_32bpp,
1034         LineTo_NOP_32bpp,
1035         LineTo_MERGENOTPEN_32bpp,
1036         LineTo_COPYPEN_32bpp,
1037         LineTo_MERGEPENNOT_32bpp,
1038         LineTo_MERGEPEN_32bpp,
1039         LineTo_WHITE_32bpp
1040 };
1041
1042 int LineTo_32bpp(HGDI_DC hdc, int nXEnd, int nYEnd)
1043 {
1044         pLineTo_32bpp _LineTo;
1045         int rop2 = gdi_GetROP2(hdc) - 1;
1046
1047         _LineTo = LineTo_ROP2_32bpp[rop2];
1048
1049         if (_LineTo != NULL)
1050                 return _LineTo(hdc, nXEnd, nYEnd);
1051         else
1052                 return 0;
1053 }