2 * GDI bit-blit operations
4 * Copyright 1993, 1994 Alexandre Julliard
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.
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.
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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 #include "mfdrv/metafiledrv.h"
25 #include "wine/debug.h"
28 WINE_DEFAULT_DEBUG_CHANNEL(metafile
);
30 /***********************************************************************
33 BOOL
MFDRV_PatBlt( PHYSDEV dev
, INT left
, INT top
, INT width
, INT height
, DWORD rop
)
35 MFDRV_MetaParam6( dev
, META_PATBLT
, left
, top
, width
, height
, HIWORD(rop
), LOWORD(rop
) );
40 /***********************************************************************
43 BOOL
MFDRV_BitBlt( PHYSDEV devDst
, INT xDst
, INT yDst
, INT width
, INT height
,
44 PHYSDEV devSrc
, INT xSrc
, INT ySrc
, DWORD rop
)
50 METAFILEDRV_PDEVICE
*physDevSrc
= (METAFILEDRV_PDEVICE
*)devSrc
;
51 DC
*dcSrc
= physDevSrc
->dc
;
53 GetObjectA(dcSrc
->hBitmap
, sizeof(BITMAP
), &BM
);
54 len
= sizeof(METARECORD
) + 12 * sizeof(INT16
) + BM
.bmWidthBytes
* BM
.bmHeight
;
55 if (!(mr
= HeapAlloc(GetProcessHeap(), 0, len
)))
57 mr
->rdFunction
= META_BITBLT
;
58 *(mr
->rdParm
+ 7) = BM
.bmWidth
;
59 *(mr
->rdParm
+ 8) = BM
.bmHeight
;
60 *(mr
->rdParm
+ 9) = BM
.bmWidthBytes
;
61 *(mr
->rdParm
+10) = BM
.bmPlanes
;
62 *(mr
->rdParm
+11) = BM
.bmBitsPixel
;
63 TRACE("len = %ld rop=%lx \n",len
,rop
);
64 if (GetBitmapBits(dcSrc
->hBitmap
,BM
.bmWidthBytes
* BM
.bmHeight
,
67 mr
->rdSize
= len
/ sizeof(INT16
);
68 *(mr
->rdParm
) = HIWORD(rop
);
69 *(mr
->rdParm
+ 1) = ySrc
;
70 *(mr
->rdParm
+ 2) = xSrc
;
71 *(mr
->rdParm
+ 3) = height
;
72 *(mr
->rdParm
+ 4) = width
;
73 *(mr
->rdParm
+ 5) = yDst
;
74 *(mr
->rdParm
+ 6) = xDst
;
75 ret
= MFDRV_WriteRecord( devDst
, mr
, mr
->rdSize
* 2);
79 HeapFree( GetProcessHeap(), 0, mr
);
85 /***********************************************************************
87 * this function contains TWO ways for procesing StretchBlt in metafiles,
88 * decide between rdFunction values META_STRETCHBLT or META_DIBSTRETCHBLT
89 * via #define STRETCH_VIA_DIB
91 #define STRETCH_VIA_DIB
92 #undef STRETCH_VIA_DIB
94 BOOL
MFDRV_StretchBlt( PHYSDEV devDst
, INT xDst
, INT yDst
, INT widthDst
,
95 INT heightDst
, PHYSDEV devSrc
, INT xSrc
, INT ySrc
,
96 INT widthSrc
, INT heightSrc
, DWORD rop
)
102 METAFILEDRV_PDEVICE
*physDevSrc
= (METAFILEDRV_PDEVICE
*)devSrc
;
103 DC
*dcSrc
= physDevSrc
->dc
;
104 #ifdef STRETCH_VIA_DIB
105 LPBITMAPINFOHEADER lpBMI
;
108 GetObjectA(dcSrc
->hBitmap
, sizeof(BITMAP
), &BM
);
109 #ifdef STRETCH_VIA_DIB
110 nBPP
= BM
.bmPlanes
* BM
.bmBitsPixel
;
111 len
= sizeof(METARECORD
) + 10 * sizeof(INT16
)
112 + sizeof(BITMAPINFOHEADER
) + (nBPP
!= 24 ? 1 << nBPP
: 0) * sizeof(RGBQUAD
)
113 + ((BM
.bmWidth
* nBPP
+ 31) / 32) * 4 * BM
.bmHeight
;
114 if (!(mr
= HeapAlloc( GetProcessHeap(), 0, len
)))
116 mr
->rdFunction
= META_DIBSTRETCHBLT
;
117 lpBMI
=(LPBITMAPINFOHEADER
)(mr
->rdParm
+10);
118 lpBMI
->biSize
= sizeof(BITMAPINFOHEADER
);
119 lpBMI
->biWidth
= BM
.bmWidth
;
120 lpBMI
->biHeight
= BM
.bmHeight
;
122 lpBMI
->biBitCount
= nBPP
; /* 1,4,8 or 24 */
123 lpBMI
->biClrUsed
= nBPP
!= 24 ? 1 << nBPP
: 0;
124 lpBMI
->biSizeImage
= ((lpBMI
->biWidth
* nBPP
+ 31) / 32) * 4 * lpBMI
->biHeight
;
125 lpBMI
->biCompression
= BI_RGB
;
126 lpBMI
->biXPelsPerMeter
= MulDiv(GetDeviceCaps(dcSrc
->hSelf
,LOGPIXELSX
),3937,100);
127 lpBMI
->biYPelsPerMeter
= MulDiv(GetDeviceCaps(dcSrc
->hSelf
,LOGPIXELSY
),3937,100);
128 lpBMI
->biClrImportant
= 0; /* 1 meter = 39.37 inch */
130 TRACE("MF_StretchBltViaDIB->len = %ld rop=%lx PixYPM=%ld Caps=%d\n",
131 len
,rop
,lpBMI
->biYPelsPerMeter
,GetDeviceCaps(hdcSrc
,LOGPIXELSY
));
132 if (GetDIBits(hdcSrc
,dcSrc
->w
.hBitmap
,0,(UINT
)lpBMI
->biHeight
,
133 (LPSTR
)lpBMI
+ DIB_BitmapInfoSize( (BITMAPINFO
*)lpBMI
,
135 (LPBITMAPINFO
)lpBMI
, DIB_RGB_COLORS
))
137 len
= sizeof(METARECORD
) + 15 * sizeof(INT16
) + BM
.bmWidthBytes
* BM
.bmHeight
;
138 if (!(mr
= HeapAlloc( GetProcessHeap(), 0, len
)))
140 mr
->rdFunction
= META_STRETCHBLT
;
141 *(mr
->rdParm
+10) = BM
.bmWidth
;
142 *(mr
->rdParm
+11) = BM
.bmHeight
;
143 *(mr
->rdParm
+12) = BM
.bmWidthBytes
;
144 *(mr
->rdParm
+13) = BM
.bmPlanes
;
145 *(mr
->rdParm
+14) = BM
.bmBitsPixel
;
146 TRACE("len = %ld rop=%lx \n",len
,rop
);
147 if (GetBitmapBits( dcSrc
->hBitmap
, BM
.bmWidthBytes
* BM
.bmHeight
,
151 mr
->rdSize
= len
/ sizeof(INT16
);
152 *(mr
->rdParm
) = LOWORD(rop
);
153 *(mr
->rdParm
+ 1) = HIWORD(rop
);
154 *(mr
->rdParm
+ 2) = heightSrc
;
155 *(mr
->rdParm
+ 3) = widthSrc
;
156 *(mr
->rdParm
+ 4) = ySrc
;
157 *(mr
->rdParm
+ 5) = xSrc
;
158 *(mr
->rdParm
+ 6) = heightDst
;
159 *(mr
->rdParm
+ 7) = widthDst
;
160 *(mr
->rdParm
+ 8) = yDst
;
161 *(mr
->rdParm
+ 9) = xDst
;
162 ret
= MFDRV_WriteRecord( devDst
, mr
, mr
->rdSize
* 2);
166 HeapFree( GetProcessHeap(), 0, mr
);
171 /***********************************************************************
172 * MFDRV_StretchDIBits
174 INT
MFDRV_StretchDIBits( PHYSDEV dev
, INT xDst
, INT yDst
, INT widthDst
,
175 INT heightDst
, INT xSrc
, INT ySrc
, INT widthSrc
,
176 INT heightSrc
, const void *bits
,
177 const BITMAPINFO
*info
, UINT wUsage
, DWORD dwRop
)
179 DWORD len
, infosize
, imagesize
;
182 infosize
= DIB_BitmapInfoSize(info
, wUsage
);
183 imagesize
= DIB_GetDIBImageBytes( info
->bmiHeader
.biWidth
,
184 info
->bmiHeader
.biHeight
,
185 info
->bmiHeader
.biBitCount
);
187 len
= sizeof(METARECORD
) + 10 * sizeof(WORD
) + infosize
+ imagesize
;
188 mr
= (METARECORD
*)HeapAlloc( GetProcessHeap(), 0, len
);
191 mr
->rdSize
= len
/ 2;
192 mr
->rdFunction
= META_STRETCHDIB
;
193 mr
->rdParm
[0] = LOWORD(dwRop
);
194 mr
->rdParm
[1] = HIWORD(dwRop
);
195 mr
->rdParm
[2] = wUsage
;
196 mr
->rdParm
[3] = (INT16
)heightSrc
;
197 mr
->rdParm
[4] = (INT16
)widthSrc
;
198 mr
->rdParm
[5] = (INT16
)ySrc
;
199 mr
->rdParm
[6] = (INT16
)xSrc
;
200 mr
->rdParm
[7] = (INT16
)heightDst
;
201 mr
->rdParm
[8] = (INT16
)widthDst
;
202 mr
->rdParm
[9] = (INT16
)yDst
;
203 mr
->rdParm
[10] = (INT16
)xDst
;
204 memcpy(mr
->rdParm
+ 11, info
, infosize
);
205 memcpy(mr
->rdParm
+ 11 + infosize
/ 2, bits
, imagesize
);
206 MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2 );
207 HeapFree( GetProcessHeap(), 0, mr
);
212 /***********************************************************************
213 * MFDRV_SetDIBitsToDeivce
215 INT
MFDRV_SetDIBitsToDevice( PHYSDEV dev
, INT xDst
, INT yDst
, DWORD cx
,
216 DWORD cy
, INT xSrc
, INT ySrc
, UINT startscan
,
217 UINT lines
, LPCVOID bits
, const BITMAPINFO
*info
,
221 DWORD len
, infosize
, imagesize
;
224 infosize
= DIB_BitmapInfoSize(info
, coloruse
);
225 imagesize
= DIB_GetDIBImageBytes( info
->bmiHeader
.biWidth
,
226 info
->bmiHeader
.biHeight
,
227 info
->bmiHeader
.biBitCount
);
229 len
= sizeof(METARECORD
) + 8 * sizeof(WORD
) + infosize
+ imagesize
;
230 mr
= (METARECORD
*)HeapAlloc( GetProcessHeap(), 0, len
);
233 mr
->rdSize
= len
/ 2;
234 mr
->rdFunction
= META_SETDIBTODEV
;
235 mr
->rdParm
[0] = coloruse
;
236 mr
->rdParm
[1] = lines
;
237 mr
->rdParm
[2] = startscan
;
238 mr
->rdParm
[3] = (INT16
)ySrc
;
239 mr
->rdParm
[4] = (INT16
)xSrc
;
240 mr
->rdParm
[5] = (INT16
)cy
;
241 mr
->rdParm
[6] = (INT16
)cx
;
242 mr
->rdParm
[7] = (INT16
)yDst
;
243 mr
->rdParm
[8] = (INT16
)xDst
;
244 memcpy(mr
->rdParm
+ 9, info
, infosize
);
245 memcpy(mr
->rdParm
+ 9 + infosize
/ 2, bits
, imagesize
);
246 MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2 );
247 HeapFree( GetProcessHeap(), 0, mr
);