4 * Copyright 1993 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
27 #include "mfdrv/metafiledrv.h"
28 #include "wine/debug.h"
30 WINE_DEFAULT_DEBUG_CHANNEL(metafile
);
33 /***********************************************************************
36 HBITMAP
MFDRV_SelectBitmap( PHYSDEV dev
, HBITMAP hbitmap
)
42 /******************************************************************
43 * MFDRV_CreateBrushIndirect
46 INT16
MFDRV_CreateBrushIndirect(PHYSDEV dev
, HBRUSH hBrush
)
52 METAFILEDRV_PDEVICE
*physDev
= (METAFILEDRV_PDEVICE
*)dev
;
54 if (!GetObjectA( hBrush
, sizeof(logbrush
), &logbrush
)) return -1;
56 switch(logbrush
.lbStyle
)
64 lb16
.lbStyle
= logbrush
.lbStyle
;
65 lb16
.lbColor
= logbrush
.lbColor
;
66 lb16
.lbHatch
= logbrush
.lbHatch
;
67 size
= sizeof(METARECORD
) + sizeof(LOGBRUSH16
) - 2;
68 mr
= HeapAlloc( GetProcessHeap(), 0, size
);
69 mr
->rdSize
= size
/ 2;
70 mr
->rdFunction
= META_CREATEBRUSHINDIRECT
;
71 memcpy( mr
->rdParm
, &lb16
, sizeof(LOGBRUSH16
));
81 GetObjectA((HANDLE
)logbrush
.lbHatch
, sizeof(bm
), &bm
);
82 if(bm
.bmBitsPixel
!= 1 || bm
.bmPlanes
!= 1) {
83 FIXME("Trying to store a colour pattern brush\n");
87 bmSize
= DIB_GetDIBImageBytes(bm
.bmWidth
, bm
.bmHeight
, 1);
89 size
= sizeof(METARECORD
) + sizeof(WORD
) + sizeof(BITMAPINFO
) +
90 sizeof(RGBQUAD
) + bmSize
;
92 mr
= HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY
, size
);
94 mr
->rdFunction
= META_DIBCREATEPATTERNBRUSH
;
95 mr
->rdSize
= size
/ 2;
96 mr
->rdParm
[0] = BS_PATTERN
;
97 mr
->rdParm
[1] = DIB_RGB_COLORS
;
98 info
= (BITMAPINFO
*)(mr
->rdParm
+ 2);
100 info
->bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
);
101 info
->bmiHeader
.biWidth
= bm
.bmWidth
;
102 info
->bmiHeader
.biHeight
= bm
.bmHeight
;
103 info
->bmiHeader
.biPlanes
= 1;
104 info
->bmiHeader
.biBitCount
= 1;
105 bits
= ((BYTE
*)info
) + sizeof(BITMAPINFO
) + sizeof(RGBQUAD
);
107 GetDIBits(physDev
->hdc
, (HANDLE
)logbrush
.lbHatch
, 0, bm
.bmHeight
,
108 bits
, info
, DIB_RGB_COLORS
);
109 *(DWORD
*)info
->bmiColors
= 0;
110 *(DWORD
*)(info
->bmiColors
+ 1) = 0xffffff;
117 DWORD bmSize
, biSize
;
119 info
= GlobalLock16((HGLOBAL16
)logbrush
.lbHatch
);
120 if (info
->bmiHeader
.biCompression
)
121 bmSize
= info
->bmiHeader
.biSizeImage
;
123 bmSize
= DIB_GetDIBImageBytes(info
->bmiHeader
.biWidth
,
124 info
->bmiHeader
.biHeight
,
125 info
->bmiHeader
.biBitCount
);
126 biSize
= DIB_BitmapInfoSize(info
, LOWORD(logbrush
.lbColor
));
127 size
= sizeof(METARECORD
) + biSize
+ bmSize
+ 2;
128 mr
= HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY
, size
);
130 mr
->rdFunction
= META_DIBCREATEPATTERNBRUSH
;
131 mr
->rdSize
= size
/ 2;
132 *(mr
->rdParm
) = logbrush
.lbStyle
;
133 *(mr
->rdParm
+ 1) = LOWORD(logbrush
.lbColor
);
134 memcpy(mr
->rdParm
+ 2, info
, biSize
+ bmSize
);
138 FIXME("Unkonwn brush style %x\n", logbrush
.lbStyle
);
141 index
= MFDRV_AddHandleDC( dev
);
142 if(!MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2))
144 HeapFree(GetProcessHeap(), 0, mr
);
150 /***********************************************************************
153 HBRUSH
MFDRV_SelectBrush( PHYSDEV dev
, HBRUSH hbrush
)
158 index
= MFDRV_CreateBrushIndirect( dev
, hbrush
);
159 if(index
== -1) return 0;
161 mr
.rdSize
= sizeof(mr
) / 2;
162 mr
.rdFunction
= META_SELECTOBJECT
;
163 mr
.rdParm
[0] = index
;
164 return MFDRV_WriteRecord( dev
, &mr
, mr
.rdSize
* 2) ? hbrush
: 0;
167 /******************************************************************
168 * MFDRV_CreateFontIndirect
171 static BOOL
MFDRV_CreateFontIndirect(PHYSDEV dev
, HFONT hFont
, LOGFONT16
*logfont
)
174 char buffer
[sizeof(METARECORD
) - 2 + sizeof(LOGFONT16
)];
175 METARECORD
*mr
= (METARECORD
*)&buffer
;
177 mr
->rdSize
= (sizeof(METARECORD
) + sizeof(LOGFONT16
) - 2) / 2;
178 mr
->rdFunction
= META_CREATEFONTINDIRECT
;
179 memcpy(&(mr
->rdParm
), logfont
, sizeof(LOGFONT16
));
180 if (!(MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2))) return FALSE
;
182 mr
->rdSize
= sizeof(METARECORD
) / 2;
183 mr
->rdFunction
= META_SELECTOBJECT
;
185 if ((index
= MFDRV_AddHandleDC( dev
)) == -1) return FALSE
;
186 *(mr
->rdParm
) = index
;
187 return MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2);
191 /***********************************************************************
194 HFONT
MFDRV_SelectFont( PHYSDEV dev
, HFONT hfont
)
198 if (!GetObject16( HFONT_16(hfont
), sizeof(lf16
), &lf16
)) return HGDI_ERROR
;
199 if (MFDRV_CreateFontIndirect(dev
, hfont
, &lf16
)) return 0;
203 /******************************************************************
204 * MFDRV_CreatePenIndirect
206 static BOOL
MFDRV_CreatePenIndirect(PHYSDEV dev
, HPEN hPen
, LOGPEN16
*logpen
)
209 char buffer
[sizeof(METARECORD
) - 2 + sizeof(*logpen
)];
210 METARECORD
*mr
= (METARECORD
*)&buffer
;
212 mr
->rdSize
= (sizeof(METARECORD
) + sizeof(*logpen
) - 2) / 2;
213 mr
->rdFunction
= META_CREATEPENINDIRECT
;
214 memcpy(&(mr
->rdParm
), logpen
, sizeof(*logpen
));
215 if (!(MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2))) return FALSE
;
217 mr
->rdSize
= sizeof(METARECORD
) / 2;
218 mr
->rdFunction
= META_SELECTOBJECT
;
220 if ((index
= MFDRV_AddHandleDC( dev
)) == -1) return FALSE
;
221 *(mr
->rdParm
) = index
;
222 return MFDRV_WriteRecord( dev
, mr
, mr
->rdSize
* 2);
226 /***********************************************************************
229 HPEN
MFDRV_SelectPen( PHYSDEV dev
, HPEN hpen
)
233 if (!GetObject16( HPEN_16(hpen
), sizeof(logpen
), &logpen
)) return 0;
234 if (MFDRV_CreatePenIndirect( dev
, hpen
, &logpen
)) return hpen
;