[PATCH v2 2/4] gdiplus: Play all EMF records using PlayEnhMetaFileRecord.

Shawn M. Chapla schapla at codeweavers.com
Tue Jun 30 12:04:02 CDT 2020


Signed-off-by: Shawn M. Chapla <schapla at codeweavers.com>
---
 dlls/gdiplus/gdiplus_private.h |   1 -
 dlls/gdiplus/metafile.c        | 124 ++++++---------------------------
 dlls/gdiplus/tests/metafile.c  |   4 +-
 3 files changed, 24 insertions(+), 105 deletions(-)

diff --git a/dlls/gdiplus/gdiplus_private.h b/dlls/gdiplus/gdiplus_private.h
index d62860360a..2ceaeade01 100644
--- a/dlls/gdiplus/gdiplus_private.h
+++ b/dlls/gdiplus/gdiplus_private.h
@@ -416,7 +416,6 @@ struct GpMetafile{
     GpRectF src_rect;
     HANDLETABLE *handle_table;
     int handle_count;
-    XFORM gdiworldtransform;
     GpMatrix *world_transform;
     GpUnit page_unit;
     REAL page_scale;
diff --git a/dlls/gdiplus/metafile.c b/dlls/gdiplus/metafile.c
index f0dacab498..9ab8b1325f 100644
--- a/dlls/gdiplus/metafile.c
+++ b/dlls/gdiplus/metafile.c
@@ -1644,50 +1644,12 @@ GpStatus WINGDIPAPI GdipGetHemfFromMetafile(GpMetafile *metafile, HENHMETAFILE *
     return Ok;
 }
 
-static void METAFILE_GetFinalGdiTransform(const GpMetafile *metafile, XFORM *result)
-{
-    const GpRectF *rect;
-    const GpPointF *pt;
-
-    /* This transforms metafile device space to output points. */
-    rect = &metafile->src_rect;
-    pt = metafile->playback_points;
-    result->eM11 = (pt[1].X - pt[0].X) / rect->Width;
-    result->eM21 = (pt[2].X - pt[0].X) / rect->Height;
-    result->eDx = pt[0].X - result->eM11 * rect->X - result->eM21 * rect->Y;
-    result->eM12 = (pt[1].Y - pt[0].Y) / rect->Width;
-    result->eM22 = (pt[2].Y - pt[0].Y) / rect->Height;
-    result->eDy = pt[0].Y - result->eM12 * rect->X - result->eM22 * rect->Y;
-}
-
-static GpStatus METAFILE_PlaybackUpdateGdiTransform(GpMetafile *metafile)
-{
-    XFORM combined, final;
-
-    METAFILE_GetFinalGdiTransform(metafile, &final);
-
-    CombineTransform(&combined, &metafile->gdiworldtransform, &final);
-
-    SetGraphicsMode(metafile->playback_dc, GM_ADVANCED);
-    SetWorldTransform(metafile->playback_dc, &combined);
-
-    return Ok;
-}
-
 static GpStatus METAFILE_PlaybackGetDC(GpMetafile *metafile)
 {
     GpStatus stat = Ok;
 
     stat = GdipGetDC(metafile->playback_graphics, &metafile->playback_dc);
 
-    if (stat == Ok)
-    {
-        static const XFORM identity = {1, 0, 0, 1, 0, 0};
-
-        metafile->gdiworldtransform = identity;
-        METAFILE_PlaybackUpdateGdiTransform(metafile);
-    }
-
     return stat;
 }
 
@@ -2528,71 +2490,22 @@ GpStatus WINGDIPAPI GdipPlayMetafileRecord(GDIPCONST GpMetafile *metafile,
         /* regular EMF record */
         if (metafile->playback_dc)
         {
-            switch (recordType)
-            {
-            case EMR_SETMAPMODE:
-            case EMR_SAVEDC:
-            case EMR_RESTOREDC:
-            case EMR_SETWINDOWORGEX:
-            case EMR_SETWINDOWEXTEX:
-            case EMR_SETVIEWPORTORGEX:
-            case EMR_SETVIEWPORTEXTEX:
-            case EMR_SCALEVIEWPORTEXTEX:
-            case EMR_SCALEWINDOWEXTEX:
-            case EMR_MODIFYWORLDTRANSFORM:
-                FIXME("not implemented for record type %x\n", recordType);
-                break;
-            case EMR_SETWORLDTRANSFORM:
-            {
-                const XFORM* xform = (void*)data;
-                real_metafile->gdiworldtransform = *xform;
-                METAFILE_PlaybackUpdateGdiTransform(real_metafile);
-                break;
-            }
-            case EMR_EXTSELECTCLIPRGN:
-            {
-                DWORD rgndatasize = *(DWORD*)data;
-                DWORD mode = *(DWORD*)(data + 4);
-                const RGNDATA *rgndata = (const RGNDATA*)(data + 8);
-                HRGN hrgn = NULL;
-
-                if (dataSize > 8)
-                {
-                    XFORM final;
-
-                    METAFILE_GetFinalGdiTransform(metafile, &final);
-
-                    hrgn = ExtCreateRegion(&final, rgndatasize, rgndata);
-                }
-
-                ExtSelectClipRgn(metafile->playback_dc, hrgn, mode);
-
-                DeleteObject(hrgn);
+            ENHMETARECORD *record = heap_alloc_zero(dataSize + 8);
 
-                return Ok;
-            }
-            default:
+            if (record)
             {
-                ENHMETARECORD *record = heap_alloc_zero(dataSize + 8);
-
-                if (record)
-                {
-                    record->iType = recordType;
-                    record->nSize = dataSize + 8;
-                    memcpy(record->dParm, data, dataSize);
-
-                    if(PlayEnhMetaFileRecord(metafile->playback_dc, metafile->handle_table,
-                            record, metafile->handle_count) == 0)
-                        ERR("PlayEnhMetaFileRecord failed\n");
+                record->iType = recordType;
+                record->nSize = dataSize + 8;
+                memcpy(record->dParm, data, dataSize);
 
-                    heap_free(record);
-                }
-                else
-                    return OutOfMemory;
+                if(PlayEnhMetaFileRecord(metafile->playback_dc, metafile->handle_table,
+                        record, metafile->handle_count) == 0)
+                    ERR("PlayEnhMetaFileRecord failed\n");
 
-                break;
-            }
+                heap_free(record);
             }
+            else
+                return OutOfMemory;
         }
     }
     else
@@ -3496,6 +3409,7 @@ GpStatus WINGDIPAPI GdipEnumerateMetafileSrcRectDestPoints(GpGraphics *graphics,
     GpMetafile *real_metafile = (GpMetafile*)metafile; /* whoever made this const was joking */
     GraphicsContainer state;
     GpPath *dst_path;
+    RECT dst_bounds;
 
     TRACE("(%p,%p,%p,%i,%p,%i,%p,%p,%p)\n", graphics, metafile,
         destPoints, count, srcRect, srcUnit, callback, callbackData,
@@ -3585,13 +3499,19 @@ GpStatus WINGDIPAPI GdipEnumerateMetafileSrcRectDestPoints(GpGraphics *graphics,
             stat = METAFILE_PlaybackUpdateClip(real_metafile);
         }
 
-        if (stat == Ok && (metafile->metafile_type == MetafileTypeEmf ||
-            metafile->metafile_type == MetafileTypeWmfPlaceable ||
-            metafile->metafile_type == MetafileTypeWmf))
+        if (stat == Ok)
+        {
             stat = METAFILE_PlaybackGetDC(real_metafile);
 
+            dst_bounds.left = real_metafile->playback_points[0].X;
+            dst_bounds.right = real_metafile->playback_points[1].X;
+            dst_bounds.top = real_metafile->playback_points[0].Y;
+            dst_bounds.bottom = real_metafile->playback_points[2].Y;
+        }
+
         if (stat == Ok)
-            EnumEnhMetaFile(0, metafile->hemf, enum_metafile_proc, &data, NULL);
+            EnumEnhMetaFile(real_metafile->playback_dc, metafile->hemf, enum_metafile_proc,
+                &data, &dst_bounds);
 
         METAFILE_PlaybackReleaseDC(real_metafile);
 
diff --git a/dlls/gdiplus/tests/metafile.c b/dlls/gdiplus/tests/metafile.c
index c8bb89a776..f3b817b3de 100644
--- a/dlls/gdiplus/tests/metafile.c
+++ b/dlls/gdiplus/tests/metafile.c
@@ -2933,7 +2933,7 @@ static void test_restoredc(void)
 
     stat = GdipBitmapGetPixel(bitmap, 21, 21, &color);
     expect(Ok, stat);
-    todo_wine expect(0xff0000ff, color);
+    expect(0xff0000ff, color);
 
     stat = GdipBitmapGetPixel(bitmap, 41, 41, &color);
     expect(Ok, stat);
@@ -2941,7 +2941,7 @@ static void test_restoredc(void)
 
     stat = GdipBitmapGetPixel(bitmap, 61, 61, &color);
     expect(Ok, stat);
-    todo_wine expect(0xff0000ff, color);
+    expect(0xff0000ff, color);
 
     stat = GdipDeleteGraphics(graphics);
     expect(Ok, stat);
-- 
2.27.0




More information about the wine-devel mailing list