Nikolay Sivov : oleaut32: Implement DISPID_PICT_RENDER dispid.

Alexandre Julliard julliard at winehq.org
Mon Mar 3 13:20:09 CST 2014


Module: wine
Branch: master
Commit: bc50be98c9c983545966d6c490c129651e0c56d6
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=bc50be98c9c983545966d6c490c129651e0c56d6

Author: Nikolay Sivov <nsivov at codeweavers.com>
Date:   Fri Feb 28 16:57:19 2014 +0400

oleaut32: Implement DISPID_PICT_RENDER dispid.

---

 dlls/oleaut32/olepicture.c       |   37 +++++++++++-
 dlls/oleaut32/tests/olepicture.c |  123 ++++++++++++++++++++++++++++++++------
 2 files changed, 142 insertions(+), 18 deletions(-)

diff --git a/dlls/oleaut32/olepicture.c b/dlls/oleaut32/olepicture.c
index 2139fde..6e4a737 100644
--- a/dlls/oleaut32/olepicture.c
+++ b/dlls/oleaut32/olepicture.c
@@ -1995,6 +1995,7 @@ static HRESULT WINAPI OLEPictureImpl_Invoke(
   UINT*     puArgErr)
 {
   OLEPictureImpl *This = impl_from_IDispatch(iface);
+  HRESULT hr;
 
   /* validate parameters */
 
@@ -2052,7 +2053,7 @@ static HRESULT WINAPI OLEPictureImpl_Invoke(
     else if (wFlags & DISPATCH_PROPERTYPUT)
     {
       VARIANTARG vararg;
-      HRESULT hr;
+
       TRACE("DISPID_PICT_HPAL\n");
 
       VariantInit(&vararg);
@@ -2090,6 +2091,40 @@ static HRESULT WINAPI OLEPictureImpl_Invoke(
       return IPicture_get_Height(&This->IPicture_iface, &V_I4(pVarResult));
     }
     break;
+  case DISPID_PICT_RENDER:
+    if (wFlags & DISPATCH_METHOD)
+    {
+      VARIANTARG *args = pDispParams->rgvarg;
+      int i;
+
+      TRACE("DISPID_PICT_RENDER\n");
+
+      if (pDispParams->cArgs != 10)
+        return DISP_E_BADPARAMCOUNT;
+
+      /* All parameters are supposed to be VT_I4 (on 64 bits too). */
+      for (i = 0; i < pDispParams->cArgs; i++)
+        if (V_VT(&args[i]) != VT_I4)
+        {
+          ERR("DISPID_PICT_RENDER: wrong argument type %d:%d\n", i, V_VT(&args[i]));
+          return DISP_E_TYPEMISMATCH;
+        }
+
+      /* FIXME: rectangle pointer argument handling seems broken on 64 bits,
+                currently Render() doesn't use it at all so for now NULL is passed. */
+      return IPicture_Render(&This->IPicture_iface,
+                LongToHandle(V_I4(&args[9])),
+                             V_I4(&args[8]),
+                             V_I4(&args[7]),
+                             V_I4(&args[6]),
+                             V_I4(&args[5]),
+                             V_I4(&args[4]),
+                             V_I4(&args[3]),
+                             V_I4(&args[2]),
+                             V_I4(&args[1]),
+                                      NULL);
+    }
+    break;
   }
 
   ERR("invalid dispid 0x%x or wFlags 0x%x\n", dispIdMember, wFlags);
diff --git a/dlls/oleaut32/tests/olepicture.c b/dlls/oleaut32/tests/olepicture.c
index de37322..26395b9 100644
--- a/dlls/oleaut32/tests/olepicture.c
+++ b/dlls/oleaut32/tests/olepicture.c
@@ -412,12 +412,14 @@ static void test_Invoke(void)
 {
     IPictureDisp *picdisp;
     HRESULT hr;
-    VARIANTARG vararg;
+    VARIANTARG vararg, args[10];
     DISPPARAMS dispparams;
     VARIANT varresult;
     IStream *stream;
     HGLOBAL hglob;
     void *data;
+    HDC hdc;
+    int i;
 
     hglob = GlobalAlloc (0, sizeof(gifimage));
     data = GlobalLock(hglob);
@@ -477,6 +479,44 @@ static void test_Invoke(void)
     hr = IPictureDisp_Invoke(picdisp, DISPID_PICT_HPAL, &IID_NULL, 0, DISPATCH_PROPERTYGET, &dispparams, &varresult, NULL, NULL);
     ok(hr == DISP_E_BADPARAMCOUNT, "IPictureDisp_Invoke should have returned DISP_E_BADPARAMCOUNT instead of 0x%08x\n", hr);
 
+    /* DISPID_PICT_RENDER */
+    hdc = GetDC(0);
+
+    for (i = 0; i < sizeof(args)/sizeof(args[0]); i++)
+        V_VT(&args[i]) = VT_I4;
+
+    V_I4(&args[0]) = 0;
+    V_I4(&args[1]) = 10;
+    V_I4(&args[2]) = 10;
+    V_I4(&args[3]) = 0;
+    V_I4(&args[4]) = 0;
+    V_I4(&args[5]) = 10;
+    V_I4(&args[6]) = 10;
+    V_I4(&args[7]) = 0;
+    V_I4(&args[8]) = 0;
+    V_I4(&args[9]) = HandleToLong(hdc);
+
+    dispparams.rgvarg = args;
+    dispparams.rgdispidNamedArgs = NULL;
+    dispparams.cArgs = 10;
+    dispparams.cNamedArgs = 0;
+
+    V_VT(&varresult) = VT_EMPTY;
+    hr = IPictureDisp_Invoke(picdisp, DISPID_PICT_RENDER, &GUID_NULL, 0, DISPATCH_METHOD, &dispparams, &varresult, NULL, NULL);
+    ok(hr == S_OK, "got 0x%08x\n", hr);
+
+    /* Try with one argument set to VT_I2, it'd still work if coerced. */
+    V_VT(&args[3]) = VT_I2;
+    hr = IPictureDisp_Invoke(picdisp, DISPID_PICT_RENDER, &GUID_NULL, 0, DISPATCH_METHOD, &dispparams, &varresult, NULL, NULL);
+    ok(hr == DISP_E_TYPEMISMATCH, "got 0x%08x\n", hr);
+    V_VT(&args[3]) = VT_I4;
+
+    /* Wrong argument count */
+    dispparams.cArgs = 9;
+    hr = IPictureDisp_Invoke(picdisp, DISPID_PICT_RENDER, &GUID_NULL, 0, DISPATCH_METHOD, &dispparams, &varresult, NULL, NULL);
+    ok(hr == DISP_E_BADPARAMCOUNT, "got 0x%08x\n", hr);
+
+    ReleaseDC(NULL, hdc);
     IPictureDisp_Release(picdisp);
 }
 
@@ -602,6 +642,55 @@ static void test_enhmetafile(void)
     IStream_Release(stream);
 }
 
+static HRESULT picture_render(IPicture *iface, HDC hdc, LONG x, LONG y, LONG cx, LONG cy,
+                              OLE_XPOS_HIMETRIC xSrc,
+                              OLE_YPOS_HIMETRIC ySrc,
+                              OLE_XSIZE_HIMETRIC cxSrc,
+                              OLE_YSIZE_HIMETRIC cySrc,
+                              const RECT *bounds)
+{
+    VARIANT ret, args[10];
+    HRESULT hr, hr_disp;
+    DISPPARAMS params;
+    IDispatch *disp;
+    int i;
+
+    hr = IPicture_Render(iface, hdc, x, y, cx, cy, xSrc, ySrc, cxSrc, cySrc, bounds);
+
+    IPicture_QueryInterface(iface, &IID_IDispatch, (void**)&disp);
+
+    /* This is broken on 64 bits - accepted pointer argument type is still VT_I4 */
+    for (i = 0; i < sizeof(args)/sizeof(args[0]); i++)
+        V_VT(&args[i]) = VT_I4;
+
+    /* pack arguments and call */
+    V_INT_PTR(&args[0]) = (INT_PTR)bounds;
+    V_I4(&args[1]) = cySrc;
+    V_I4(&args[2]) = cxSrc;
+    V_I4(&args[3]) = ySrc;
+    V_I4(&args[4]) = xSrc;
+    V_I4(&args[5]) = cy;
+    V_I4(&args[6]) = cx;
+    V_I4(&args[7]) = y;
+    V_I4(&args[8]) = x;
+    V_I4(&args[9]) = HandleToLong(hdc);
+
+    params.rgvarg = args;
+    params.rgdispidNamedArgs = NULL;
+    params.cArgs = 10;
+    params.cNamedArgs = 0;
+
+    V_VT(&ret) = VT_EMPTY;
+    hr_disp = IDispatch_Invoke(disp, DISPID_PICT_RENDER, &GUID_NULL, 0, DISPATCH_METHOD,
+        &params, &ret, NULL, NULL);
+    ok(hr == hr_disp, "DISPID_PICT_RENDER returned wrong code, 0x%08x, expected 0x%08x\n",
+       hr_disp, hr);
+
+    IDispatch_Release(disp);
+
+    return hr;
+}
+
 static void test_Render(void)
 {
     IPicture *pic;
@@ -619,22 +708,22 @@ static void test_Render(void)
     ok(hres == S_OK, "IPicture_get_Type does not return S_OK, but 0x%08x\n", hres);
     ok(type == PICTYPE_UNINITIALIZED, "Expected type = PICTYPE_UNINITIALIZED, got = %d\n", type);
     /* zero dimensions */
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 0, 0, 0, 0, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 0, 0, 0, 0, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 10, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 10, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 0, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 0, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 0, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 0, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
     /* nonzero dimensions, PICTYPE_UNINITIALIZED */
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 10, NULL);
     ole_expect(hres, S_OK);
     IPicture_Release(pic);
 
@@ -649,19 +738,19 @@ static void test_Render(void)
 
     OleCreatePictureIndirect(&desc, &IID_IPicture, TRUE, (VOID**)&pic);
     /* zero dimensions, PICTYPE_ICON */
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 0, 0, 0, 0, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 0, 0, 0, 0, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 10, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 0, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 10, 0, 0, 0, 0, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 10, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 10, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 10, 0, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 10, 0, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
-    hres = IPicture_Render(pic, hdc, 0, 0, 0, 0, 0, 0, 10, 10, NULL);
+    hres = picture_render(pic, hdc, 0, 0, 0, 0, 0, 0, 10, 10, NULL);
     ole_expect(hres, CTL_E_INVALIDPROPERTYVALUE);
 
     /* Check if target size and position is respected */
@@ -673,7 +762,7 @@ static void test_Render(void)
     SetPixelV(hdc, 10, 10, 0x00223344);
     expected = GetPixel(hdc, 0, 0);
 
-    hres = IPicture_Render(pic, hdc, 1, 1, 9, 9, 0, 0, pWidth, -pHeight, NULL);
+    hres = picture_render(pic, hdc, 1, 1, 9, 9, 0, 0, pWidth, -pHeight, NULL);
     ole_expect(hres, S_OK);
 
     if(hres != S_OK) {




More information about the wine-cvs mailing list