Commit c5235eea authored by Alistair Leslie-Hughes's avatar Alistair Leslie-Hughes Committed by Alexandre Julliard

gdi32: Add EnhMetafile PolyBezier, PolyBezierTo support.

parent a4ee9f2d
...@@ -94,6 +94,8 @@ extern BOOL EMFDRV_PaintRgn( PHYSDEV dev, HRGN hrgn ) DECLSPEC_HIDDEN; ...@@ -94,6 +94,8 @@ extern BOOL EMFDRV_PaintRgn( PHYSDEV dev, HRGN hrgn ) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_PatBlt( PHYSDEV dev, struct bitblt_coords *dst, DWORD rop ) DECLSPEC_HIDDEN; extern BOOL EMFDRV_PatBlt( PHYSDEV dev, struct bitblt_coords *dst, DWORD rop ) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_Pie( PHYSDEV dev, INT left, INT top, INT right, INT bottom, extern BOOL EMFDRV_Pie( PHYSDEV dev, INT left, INT top, INT right, INT bottom,
INT xstart, INT ystart, INT xend, INT yend ) DECLSPEC_HIDDEN; INT xstart, INT ystart, INT xend, INT yend ) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_PolyBezier( PHYSDEV dev, const POINT *pts, DWORD count ) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_PolyBezierTo( PHYSDEV dev, const POINT *pts, DWORD count ) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_PolyPolygon( PHYSDEV dev, const POINT* pt, const INT* counts, UINT polys) DECLSPEC_HIDDEN; extern BOOL EMFDRV_PolyPolygon( PHYSDEV dev, const POINT* pt, const INT* counts, UINT polys) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_PolyPolyline( PHYSDEV dev, const POINT* pt, const DWORD* counts, DWORD polys) DECLSPEC_HIDDEN; extern BOOL EMFDRV_PolyPolyline( PHYSDEV dev, const POINT* pt, const DWORD* counts, DWORD polys) DECLSPEC_HIDDEN;
extern BOOL EMFDRV_Polygon( PHYSDEV dev, const POINT* pt, INT count ) DECLSPEC_HIDDEN; extern BOOL EMFDRV_Polygon( PHYSDEV dev, const POINT* pt, INT count ) DECLSPEC_HIDDEN;
......
...@@ -451,6 +451,26 @@ BOOL EMFDRV_Polygon( PHYSDEV dev, const POINT* pt, INT count ) ...@@ -451,6 +451,26 @@ BOOL EMFDRV_Polygon( PHYSDEV dev, const POINT* pt, INT count )
return EMFDRV_Polylinegon( dev, pt, count, EMR_POLYGON ); return EMFDRV_Polylinegon( dev, pt, count, EMR_POLYGON );
} }
/**********************************************************************
* EMFDRV_PolyBezier
*/
BOOL EMFDRV_PolyBezier( PHYSDEV dev, const POINT *pts, DWORD count )
{
if(EMFDRV_Polylinegon16( dev, pts, count, EMR_POLYBEZIER16 ))
return TRUE;
return EMFDRV_Polylinegon( dev, pts, count, EMR_POLYBEZIER );
}
/**********************************************************************
* EMFDRV_PolyBezierTo
*/
BOOL EMFDRV_PolyBezierTo( PHYSDEV dev, const POINT *pts, DWORD count )
{
if(EMFDRV_Polylinegon16( dev, pts, count, EMR_POLYBEZIERTO16 ))
return TRUE;
return EMFDRV_Polylinegon( dev, pts, count, EMR_POLYBEZIERTO );
}
/********************************************************************** /**********************************************************************
* EMFDRV_PolyPolylinegon * EMFDRV_PolyPolylinegon
......
...@@ -109,8 +109,8 @@ static const struct gdi_dc_funcs EMFDRV_Funcs = ...@@ -109,8 +109,8 @@ static const struct gdi_dc_funcs EMFDRV_Funcs =
EMFDRV_PaintRgn, /* pPaintRgn */ EMFDRV_PaintRgn, /* pPaintRgn */
EMFDRV_PatBlt, /* pPatBlt */ EMFDRV_PatBlt, /* pPatBlt */
EMFDRV_Pie, /* pPie */ EMFDRV_Pie, /* pPie */
NULL, /* pPolyBezier */ EMFDRV_PolyBezier, /* pPolyBezier */
NULL, /* pPolyBezierTo */ EMFDRV_PolyBezierTo, /* pPolyBezierTo */
NULL, /* pPolyDraw */ NULL, /* pPolyDraw */
EMFDRV_PolyPolygon, /* pPolyPolygon */ EMFDRV_PolyPolygon, /* pPolyPolygon */
EMFDRV_PolyPolyline, /* pPolyPolyline */ EMFDRV_PolyPolyline, /* pPolyPolyline */
......
...@@ -1321,6 +1321,51 @@ static const unsigned char EMF_DCBRUSH_BITS[] = ...@@ -1321,6 +1321,51 @@ static const unsigned char EMF_DCBRUSH_BITS[] =
0x14, 0x00, 0x00, 0x00 0x14, 0x00, 0x00, 0x00
}; };
static const unsigned char EMF_BEZIER_BITS[] =
{
0x01, 0x00, 0x00, 0x00, 0x6c, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x01, 0x80, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x1a, 0x2a, 0x0d, 0x00, 0x1a, 0x2f, 0x0d, 0x00,
0x20, 0x45, 0x4d, 0x46, 0x00, 0x00, 0x01, 0x00,
0x44, 0x01, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x05, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
0x51, 0x01, 0x00, 0x00, 0x0e, 0x01, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x68, 0x24, 0x05, 0x00,
0xb0, 0x1e, 0x04, 0x00, 0x58, 0x00, 0x00, 0x00,
0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
0x14, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
0x0a, 0x00, 0x0a, 0x00, 0x14, 0x00, 0x14, 0x00,
0x0f, 0x00, 0x0f, 0x00, 0x55, 0x00, 0x00, 0x00,
0x2c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
0x0a, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00,
0x19, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
0x0a, 0x00, 0x0a, 0x00, 0x14, 0x00, 0x14, 0x00,
0x0f, 0x00, 0x0f, 0x00, 0x19, 0x00, 0x19, 0x00,
0x02, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00,
0x0f, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00,
0x01, 0x80, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00,
0x04, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00,
0x01, 0x80, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
0x14, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00,
0x0f, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00,
0x19, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00,
0x34, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00,
0x0f, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00,
0x01, 0x80, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
0x01, 0x80, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00,
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
0x0f, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00,
0x0e, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00,
0x14, 0x00, 0x00, 0x00
};
/* For debugging or dumping the raw metafiles produced by /* For debugging or dumping the raw metafiles produced by
* new test functions. * new test functions.
*/ */
...@@ -1588,6 +1633,28 @@ static BOOL match_emf_record(const ENHMETARECORD *emr1, const ENHMETARECORD *emr ...@@ -1588,6 +1633,28 @@ static BOOL match_emf_record(const ENHMETARECORD *emr1, const ENHMETARECORD *emr
HeapFree(GetProcessHeap(), 0, emr_nt4); HeapFree(GetProcessHeap(), 0, emr_nt4);
} }
} }
else if (emr1->iType == EMR_POLYBEZIERTO16 || emr1->iType == EMR_POLYBEZIER16)
{
EMRPOLYBEZIER16 *eto1, *eto2;
eto1 = (EMRPOLYBEZIER16*)emr1;
eto2 = (EMRPOLYBEZIER16*)emr2;
diff = eto1->cpts != eto1->cpts;
if(!diff)
diff = memcmp(eto1->apts, eto2->apts, eto1->cpts * sizeof(POINTS));
}
else if (emr1->iType == EMR_POLYBEZIERTO || emr1->iType == EMR_POLYBEZIER)
{
EMRPOLYBEZIER *eto1, *eto2;
eto1 = (EMRPOLYBEZIER*)emr1;
eto2 = (EMRPOLYBEZIER*)emr2;
diff = eto1->cptl != eto1->cptl;
if(!diff)
diff = memcmp(eto1->aptl, eto2->aptl, eto1->cptl * sizeof(POINTL));
}
else else
diff = memcmp(emr1, emr2, emr1->nSize); diff = memcmp(emr1, emr2, emr1->nSize);
...@@ -1658,17 +1725,17 @@ static int compare_emf_bits(const HENHMETAFILE mf, const unsigned char *bits, ...@@ -1658,17 +1725,17 @@ static int compare_emf_bits(const HENHMETAFILE mf, const unsigned char *bits,
offset2 = emh2->nSize; /* Needed for Win9x/WinME/NT4 */ offset2 = emh2->nSize; /* Needed for Win9x/WinME/NT4 */
while (offset1 < emh1->nBytes) while (offset1 < emh1->nBytes)
{ {
const ENHMETARECORD *emr1 = (const ENHMETARECORD *)(bits + offset1); const ENHMETARECORD *emr1 = (const ENHMETARECORD *)(bits + offset1);
const ENHMETARECORD *emr2 = (const ENHMETARECORD *)(buf + offset2); const ENHMETARECORD *emr2 = (const ENHMETARECORD *)(buf + offset2);
trace("%s: EMF record %u, size %u/record %u, size %u\n", trace("%s: EMF record %u, size %u/record %u, size %u\n",
desc, emr1->iType, emr1->nSize, emr2->iType, emr2->nSize); desc, emr1->iType, emr1->nSize, emr2->iType, emr2->nSize);
if (!match_emf_record(emr1, emr2, desc, ignore_scaling)) return -1; if (!match_emf_record(emr1, emr2, desc, ignore_scaling)) return -1;
/* We have already bailed out if iType or nSize don't match */ /* We have already bailed out if iType or nSize don't match */
offset1 += emr1->nSize; offset1 += emr1->nSize;
offset2 += emr2->nSize; offset2 += emr2->nSize;
} }
return 0; return 0;
} }
...@@ -2250,7 +2317,7 @@ static int CALLBACK clip_emf_enum_proc(HDC hdc, HANDLETABLE *handle_table, ...@@ -2250,7 +2317,7 @@ static int CALLBACK clip_emf_enum_proc(HDC hdc, HANDLETABLE *handle_table,
{ {
if (emr->iType == EMR_EXTSELECTCLIPRGN) if (emr->iType == EMR_EXTSELECTCLIPRGN)
{ {
const EMREXTSELECTCLIPRGN *clip = (const EMREXTSELECTCLIPRGN *)emr; const EMREXTSELECTCLIPRGN *clip = (const EMREXTSELECTCLIPRGN *)emr;
union _rgn union _rgn
{ {
RGNDATA data; RGNDATA data;
...@@ -3089,6 +3156,45 @@ static void test_SetEnhMetaFileBits(void) ...@@ -3089,6 +3156,45 @@ static void test_SetEnhMetaFileBits(void)
DeleteEnhMetaFile(hemf); DeleteEnhMetaFile(hemf);
} }
static void test_emf_polybezier(void)
{
HDC hdcMetafile;
HENHMETAFILE hemf;
POINT pts[4];
BOOL ret;
SetLastError(0xdeadbeef);
hdcMetafile = CreateEnhMetaFileA(GetDC(0), NULL, NULL, NULL);
ok(hdcMetafile != 0, "CreateEnhMetaFileA error %d\n", GetLastError());
pts[0].x = pts[0].y = 10;
pts[1].x = pts[1].y = 20;
pts[2].x = pts[2].y = 15;
pts[3].x = pts[3].y = 25;
ret = PolyBezierTo(hdcMetafile, pts, 3); /* EMR_POLYBEZIERTO16 */
ok( ret, "PolyBezierTo failed\n" );
ret = PolyBezier(hdcMetafile, pts, 4); /* EMR_POLYBEZIER16 */
ok( ret, "PolyBezier failed\n" );
pts[0].x = pts[0].y = 32769;
ret = PolyBezier(hdcMetafile, pts, 4); /* EMR_POLYBEZIER */
ok( ret, "PolyBezier failed\n" );
ret = PolyBezierTo(hdcMetafile, pts, 3); /* EMR_POLYBEZIERTO */
ok( ret, "PolyBezierTo failed\n" );
hemf = CloseEnhMetaFile(hdcMetafile);
ok(hemf != 0, "CloseEnhMetaFile error %d\n", GetLastError());
if(compare_emf_bits(hemf, EMF_BEZIER_BITS, sizeof(EMF_BEZIER_BITS),
"emf_Bezier", FALSE) != 0)
{
dump_emf_bits(hemf, "emf_Bezier");
dump_emf_records(hemf, "emf_Bezier");
}
DeleteEnhMetaFile(hemf);
}
START_TEST(metafile) START_TEST(metafile)
{ {
init_function_pointers(); init_function_pointers();
...@@ -3111,6 +3217,7 @@ START_TEST(metafile) ...@@ -3111,6 +3217,7 @@ START_TEST(metafile)
test_mf_ExtTextOut_on_path(); test_mf_ExtTextOut_on_path();
test_emf_ExtTextOut_on_path(); test_emf_ExtTextOut_on_path();
test_emf_clipping(); test_emf_clipping();
test_emf_polybezier();
/* For metafile conversions */ /* For metafile conversions */
test_mf_conversions(); test_mf_conversions();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment