1/*
2 * gdiplusmetafile.h
3 *
4 * GDI+ Metafile class
5 *
6 * This file is part of the w32api package.
7 *
8 * Contributors:
9 *   Created by Markus Koenig <markus@stber-koenig.de>
10 *
11 * THIS SOFTWARE IS NOT COPYRIGHTED
12 *
13 * This source code is offered for use in the public domain. You may
14 * use, modify or distribute it freely.
15 *
16 * This code is distributed in the hope that it will be useful but
17 * WITHOUT ANY WARRANTY. ALL WARRANTIES, EXPRESS OR IMPLIED ARE HEREBY
18 * DISCLAIMED. This includes but is not limited to warranties of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
20 *
21 */
22
23#ifndef __GDIPLUS_METAFILE_H
24#define __GDIPLUS_METAFILE_H
25#if __GNUC__ >=3
26#pragma GCC system_header
27#endif
28
29#ifndef __cplusplus
30#error "A C++ compiler is required to include gdiplusmetafile.h."
31#endif
32
33class Metafile: public Image
34{
35public:
36	static UINT EmfToWmfBits(HENHMETAFILE hEmf,
37			UINT cbData16, LPBYTE pData16,
38			INT iMapMode = MM_ANISOTROPIC,
39			EmfToWmfBitsFlags eFlags = EmfToWmfBitsFlagsDefault)
40	{
41		return DllExports::GdipEmfToWmfBits(hEmf,
42				cbData16, pData16, iMapMode, eFlags);
43	}
44	static Status GetMetafileHeader(const WCHAR *filename,
45			MetafileHeader *header)
46	{
47		return DllExports::GdipGetMetafileHeaderFromFile(
48				filename, header);
49	}
50	static Status GetMetafileHeader(IStream *stream, MetafileHeader *header)
51	{
52		return DllExports::GdipGetMetafileHeaderFromStream(
53				stream, header);
54	}
55	////TODO: Metafile::GetMetafileHeader
56	//static Status GetMetafileHeader(HMETAFILE hWmf,
57	//		const WmfPlaceableFileHeader *wmfPlaceableFileHeader,
58	//		MetafileHeader *header)
59	//{
60	//	// WTF: No flat API to do this.
61	//	return NotImplemented;
62	//}
63	static Status GetMetafileHeader(HENHMETAFILE hEmf,
64			MetafileHeader *header)
65	{
66		return DllExports::GdipGetMetafileHeaderFromEmf(hEmf, header);
67	}
68
69	Metafile(HMETAFILE hWmf,
70			const WmfPlaceableFileHeader *wmfPlaceableFileHeader,
71			BOOL deleteWmf = FALSE): Image(NULL, Ok)
72	{
73		GpMetafile *nativeMetafile = NULL;
74		lastStatus = DllExports::GdipCreateMetafileFromWmf(
75				hWmf, deleteWmf, wmfPlaceableFileHeader,
76				&nativeMetafile);
77		nativeImage = nativeMetafile;
78	}
79	Metafile(HENHMETAFILE hEmf, BOOL deleteEmf = FALSE): Image(NULL, Ok)
80	{
81		GpMetafile *nativeMetafile = NULL;
82		lastStatus = DllExports::GdipCreateMetafileFromEmf(
83				hEmf, deleteEmf, &nativeMetafile);
84		nativeImage = nativeMetafile;
85	}
86	Metafile(const WCHAR *filename): Image(NULL, Ok)
87	{
88		GpMetafile *nativeMetafile = NULL;
89		lastStatus = DllExports::GdipCreateMetafileFromFile(
90				filename, &nativeMetafile);
91		nativeImage = nativeMetafile;
92	}
93	Metafile(const WCHAR *filename,
94			const WmfPlaceableFileHeader *wmfPlaceableFileHeader):
95			Image(NULL, Ok)
96	{
97		GpMetafile *nativeMetafile = NULL;
98		lastStatus = DllExports::GdipCreateMetafileFromWmfFile(
99				filename, wmfPlaceableFileHeader,
100				&nativeMetafile);
101		nativeImage = nativeMetafile;
102	}
103	Metafile(IStream *stream): Image(NULL, Ok)
104	{
105		GpMetafile *nativeMetafile = NULL;
106		lastStatus = DllExports::GdipCreateMetafileFromStream(
107				stream, &nativeMetafile);
108		nativeImage = nativeMetafile;
109	}
110	Metafile(HDC referenceHdc, EmfType type = EmfTypeEmfPlusDual,
111			const WCHAR *description = NULL): Image(NULL, Ok)
112	{
113		GpMetafile *nativeMetafile = NULL;
114		lastStatus = DllExports::GdipRecordMetafile(
115				referenceHdc, type, NULL, MetafileFrameUnitGdi,
116				description, &nativeMetafile);
117		nativeImage = nativeMetafile;
118	}
119	Metafile(HDC referenceHdc, const RectF& frameRect,
120			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
121			EmfType type = EmfTypeEmfPlusDual,
122			const WCHAR *description = NULL): Image(NULL, Ok)
123	{
124		GpMetafile *nativeMetafile = NULL;
125		lastStatus = DllExports::GdipRecordMetafile(
126				referenceHdc, type, &frameRect, frameUnit,
127				description, &nativeMetafile);
128		nativeImage = nativeMetafile;
129	}
130	Metafile(HDC referenceHdc, const Rect& frameRect,
131			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
132			EmfType type = EmfTypeEmfPlusDual,
133			const WCHAR *description = NULL): Image(NULL, Ok)
134	{
135		GpMetafile *nativeMetafile = NULL;
136		lastStatus = DllExports::GdipRecordMetafileI(
137				referenceHdc, type, &frameRect, frameUnit,
138				description, &nativeMetafile);
139		nativeImage = nativeMetafile;
140	}
141	Metafile(const WCHAR *filename, HDC referenceHdc,
142			EmfType type = EmfTypeEmfPlusDual,
143			const WCHAR *description = NULL): Image(NULL, Ok)
144	{
145		GpMetafile *nativeMetafile = NULL;
146		lastStatus = DllExports::GdipRecordMetafileFileName(
147				filename, referenceHdc, type, NULL,
148				MetafileFrameUnitGdi, description,
149				&nativeMetafile);
150		nativeImage = nativeMetafile;
151	}
152	Metafile(const WCHAR *filename, HDC referenceHdc,
153			const RectF& frameRect,
154			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
155			EmfType type = EmfTypeEmfPlusDual,
156			const WCHAR *description = NULL): Image(NULL, Ok)
157	{
158		GpMetafile *nativeMetafile = NULL;
159		lastStatus = DllExports::GdipRecordMetafileFileName(
160				filename, referenceHdc, type, &frameRect,
161				frameUnit, description, &nativeMetafile);
162		nativeImage = nativeMetafile;
163	}
164	Metafile(const WCHAR *filename, HDC referenceHdc,
165			const Rect& frameRect,
166			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
167			EmfType type = EmfTypeEmfPlusDual,
168			const WCHAR *description = NULL): Image(NULL, Ok)
169	{
170		GpMetafile *nativeMetafile = NULL;
171		lastStatus = DllExports::GdipRecordMetafileFileNameI(
172				filename, referenceHdc, type, &frameRect,
173				frameUnit, description, &nativeMetafile);
174		nativeImage = nativeMetafile;
175	}
176	Metafile(IStream *stream, HDC referenceHdc,
177			EmfType type = EmfTypeEmfPlusDual,
178			const WCHAR *description = NULL): Image(NULL, Ok)
179	{
180		GpMetafile *nativeMetafile = NULL;
181		lastStatus = DllExports::GdipRecordMetafileStream(
182				stream, referenceHdc, type, NULL,
183				MetafileFrameUnitGdi, description,
184				&nativeMetafile);
185		nativeImage = nativeMetafile;
186	}
187	Metafile(IStream *stream, HDC referenceHdc, const RectF& frameRect,
188			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
189			EmfType type = EmfTypeEmfPlusDual,
190			const WCHAR *description = NULL): Image(NULL, Ok)
191	{
192		GpMetafile *nativeMetafile = NULL;
193		lastStatus = DllExports::GdipRecordMetafileStream(
194				stream, referenceHdc, type, &frameRect,
195				frameUnit, description, &nativeMetafile);
196		nativeImage = nativeMetafile;
197	}
198	Metafile(IStream *stream, HDC referenceHdc, const Rect& frameRect,
199			MetafileFrameUnit frameUnit = MetafileFrameUnitGdi,
200			EmfType type = EmfTypeEmfPlusDual,
201			const WCHAR *description = NULL): Image(NULL, Ok)
202	{
203		GpMetafile *nativeMetafile = NULL;
204		lastStatus = DllExports::GdipRecordMetafileStreamI(
205				stream, referenceHdc, type, &frameRect,
206				frameUnit, description, &nativeMetafile);
207		nativeImage = nativeMetafile;
208	}
209	virtual ~Metafile()
210	{
211	}
212	virtual Metafile* Clone() const
213	{
214		GpImage *cloneImage = NULL;
215		Status status = updateStatus(DllExports::GdipCloneImage(
216				nativeImage, &cloneImage));
217		if (status == Ok) {
218			Metafile *result = new Metafile(cloneImage, lastStatus);
219			if (!result) {
220				DllExports::GdipDisposeImage(cloneImage);
221				lastStatus = OutOfMemory;
222			}
223			return result;
224		} else {
225			return NULL;
226		}
227	}
228
229	////TODO: [GDI+ 1.1] Metafile::ConvertToEmfPlus
230	//Status ConvertToEmfPlus(const Graphics *refGraphics,
231	//		BOOL *conversionSuccess = NULL,
232	//		EmfType emfType = EmfTypeEmfPlusOnly,
233	//		const WCHAR *description = NULL)
234	//{
235	//	// FIXME: can't test GdipConvertToEmfPlus because it isn't exported in 1.0
236	//	return updateStatus(DllExports::GdipConvertToEmfPlus(
237	//			refGraphics ? refGraphics->nativeGraphics : NULL,
238	//			(GpMetafile*) nativeImage,
239	//			conversionSuccess, emfType, description, ???));
240	//}
241	////TODO: [GDI+ 1.1] Metafile::ConvertToEmfPlus
242	//Status ConvertToEmfPlus(const Graphics *refGraphics,
243	//		const WCHAR *filename,
244	//		BOOL *conversionSuccess = NULL,
245	//		EmfType emfType = EmfTypeEmfPlusOnly,
246	//		const WCHAR *description = NULL)
247	//{
248	//	// FIXME: can't test GdipConvertToEmfPlusToFile because it isn't exported in 1.0
249	//	return updateStatus(DllExports::GdipConvertToEmfPlusToFile(
250	//			refGraphics ? refGraphics->nativeGraphics : NULL,
251	//			(GpMetafile*) nativeImage, conversionSuccess,
252	//			filename, emfType, description, ???));
253	//}
254	////TODO: [GDI+ 1.1] Metafile::ConvertToEmfPlus
255	//Status ConvertToEmfPlus(const Graphics *refGraphics,
256	//		IStream *stream,
257	//		BOOL *conversionSuccess = NULL,
258	//		EmfType emfType = EmfTypeEmfPlusOnly,
259	//		const WCHAR *description = NULL)
260	//{
261	//	// FIXME: can't test GdipConvertToEmfPlusToStream because it isn't exported in 1.0
262	//	return updateStatus(DllExports::GdipConvertToEmfPlusToStream(
263	//			refGraphics ? refGraphics->nativeGraphics : NULL,
264	//			(GpMetafile*) nativeImage, conversionSuccess,
265	//			stream, emfType, description, ???));
266	//}
267	UINT GetDownLevelRasterizationLimit() const
268	{
269		UINT result = 0;
270		updateStatus(DllExports::GdipGetMetafileDownLevelRasterizationLimit(
271				(GpMetafile*) nativeImage, &result));
272		return result;
273	}
274	HENHMETAFILE GetHENHMETAFILE()
275	{
276		HENHMETAFILE result = NULL;
277		updateStatus(DllExports::GdipGetHemfFromMetafile(
278				(GpMetafile*) nativeImage, &result));
279		return result;
280	}
281	Status GetMetafileHeader(MetafileHeader *header) const
282	{
283		return updateStatus(DllExports::GdipGetMetafileHeaderFromMetafile(
284				(GpMetafile*) nativeImage, header));
285	}
286	Status PlayRecord(EmfPlusRecordType recordType, UINT flags,
287			UINT dataSize, const BYTE *data) const
288	{
289		return updateStatus(DllExports::GdipPlayMetafileRecord(
290				(GpMetafile*) nativeImage,
291				recordType, flags, dataSize, data));
292	}
293	Status SetDownLevelRasterizationLimit(UINT limitDpi)
294	{
295		return updateStatus(DllExports::GdipSetMetafileDownLevelRasterizationLimit(
296				(GpMetafile*) nativeImage, limitDpi));
297	}
298
299private:
300	Metafile(GpImage *image, Status status): Image(image, status) {}
301	Metafile(const Metafile&);
302	Metafile& operator=(const Metafile&);
303};
304
305#endif /* __GDIPLUS_METAFILE_H */
306