[PATCH 1/2] wincodecs: Implement CreateBitmapFromSourceRect().

Nikolay Sivov nsivov at codeweavers.com
Thu Nov 8 06:20:54 CST 2018


Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
 dlls/windowscodecs/imgfactory.c   | 46 +++++++++++++++++++++++-----
 dlls/windowscodecs/tests/bitmap.c | 51 +++++++++++++++++++++++++++++++
 2 files changed, 89 insertions(+), 8 deletions(-)

diff --git a/dlls/windowscodecs/imgfactory.c b/dlls/windowscodecs/imgfactory.c
index dbcc5f5923..78919a7387 100644
--- a/dlls/windowscodecs/imgfactory.c
+++ b/dlls/windowscodecs/imgfactory.c
@@ -486,9 +486,8 @@ static HRESULT WINAPI ImagingFactory_CreateBitmap(IWICImagingFactory2 *iface,
     return BitmapImpl_Create(uiWidth, uiHeight, 0, 0, NULL, 0, pixelFormat, option, ppIBitmap);
 }
 
-static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory2 *iface,
-    IWICBitmapSource *piBitmapSource, WICBitmapCreateCacheOption option,
-    IWICBitmap **ppIBitmap)
+static HRESULT create_bitmap_from_source_rect(IWICBitmapSource *piBitmapSource, const WICRect *rect,
+    WICBitmapCreateCacheOption option, IWICBitmap **ppIBitmap)
 {
     IWICBitmap *result;
     IWICBitmapLock *lock;
@@ -502,13 +501,20 @@ static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory2
     IWICPixelFormatInfo2 *formatinfo;
     WICPixelFormatNumericRepresentation format_type;
 
-    TRACE("(%p,%p,%u,%p)\n", iface, piBitmapSource, option, ppIBitmap);
-
     if (!piBitmapSource || !ppIBitmap)
         return E_INVALIDARG;
 
     hr = IWICBitmapSource_GetSize(piBitmapSource, &width, &height);
 
+    if (SUCCEEDED(hr) && rect)
+    {
+        if (rect->X >= width || rect->Y >= height || rect->Width == 0 || rect->Height == 0)
+            return E_INVALIDARG;
+
+        width = min(width - rect->X, rect->Width);
+        height = min(height - rect->Y, rect->Height);
+    }
+
     if (SUCCEEDED(hr))
         hr = IWICBitmapSource_GetPixelFormat(piBitmapSource, &pixelformat);
 
@@ -539,7 +545,14 @@ static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory2
         {
             UINT stride, buffersize;
             BYTE *buffer;
-            rc.X = rc.Y = 0;
+
+            if (rect)
+            {
+                rc.X = rect->X;
+                rc.Y = rect->Y;
+            }
+            else
+                rc.X = rc.Y = 0;
             rc.Width = width;
             rc.Height = height;
 
@@ -592,13 +605,30 @@ static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory2
     return hr;
 }
 
+static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory2 *iface,
+    IWICBitmapSource *piBitmapSource, WICBitmapCreateCacheOption option,
+    IWICBitmap **ppIBitmap)
+{
+    TRACE("(%p,%p,%u,%p)\n", iface, piBitmapSource, option, ppIBitmap);
+
+    return create_bitmap_from_source_rect(piBitmapSource, NULL, option, ppIBitmap);
+}
+
 static HRESULT WINAPI ImagingFactory_CreateBitmapFromSourceRect(IWICImagingFactory2 *iface,
     IWICBitmapSource *piBitmapSource, UINT x, UINT y, UINT width, UINT height,
     IWICBitmap **ppIBitmap)
 {
-    FIXME("(%p,%p,%u,%u,%u,%u,%p): stub\n", iface, piBitmapSource, x, y, width,
+    WICRect rect;
+
+    TRACE("(%p,%p,%u,%u,%u,%u,%p)\n", iface, piBitmapSource, x, y, width,
         height, ppIBitmap);
-    return E_NOTIMPL;
+
+    rect.X = x;
+    rect.Y = y;
+    rect.Width = width;
+    rect.Height = height;
+
+    return create_bitmap_from_source_rect(piBitmapSource, &rect, WICBitmapCacheOnLoad, ppIBitmap);
 }
 
 static HRESULT WINAPI ImagingFactory_CreateBitmapFromMemory(IWICImagingFactory2 *iface,
diff --git a/dlls/windowscodecs/tests/bitmap.c b/dlls/windowscodecs/tests/bitmap.c
index 6e01f0b1d1..61e985a19a 100644
--- a/dlls/windowscodecs/tests/bitmap.c
+++ b/dlls/windowscodecs/tests/bitmap.c
@@ -452,6 +452,20 @@ static void test_createbitmapfromsource(void)
     hr = IWICBitmap_SetResolution(bitmap, 12.0, 34.0);
     ok(hr == S_OK, "IWICBitmap_SetResolution failed hr=%x\n", hr);
 
+    /* WICBitmapNoCache */
+    hr = IWICImagingFactory_CreateBitmapFromSource(factory, (IWICBitmapSource *)bitmap,
+        WICBitmapNoCache, &bitmap2);
+    ok(hr == S_OK, "IWICImagingFactory_CreateBitmapFromSource failed hr=%x\n", hr);
+todo_wine
+    ok(bitmap2 == bitmap, "Unexpected bitmap instance.\n");
+
+    IWICBitmap_Release(bitmap2);
+
+    bitmap2 = (void *)0xdeadbeef;
+    hr = IWICImagingFactory_CreateBitmapFromSource(factory, &bitmapsource, WICBitmapNoCache, &bitmap2);
+    ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr);
+    ok(bitmap2 == (void *)0xdeadbeef, "Unexpected pointer %p.\n", bitmap2);
+
     hr = IWICImagingFactory_CreateBitmapFromSource(factory, (IWICBitmapSource*)bitmap,
         WICBitmapCacheOnLoad, &bitmap2);
     ok(hr == S_OK, "IWICImagingFactory_CreateBitmapFromSource failed hr=%x\n", hr);
@@ -538,6 +552,43 @@ static void test_createbitmapfromsource(void)
     ok(width == 3, "got %d, expected 3\n", width);
     ok(height == 3, "got %d, expected 3\n", height);
 
+    /* CreateBitmapFromSourceRect */
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 0, 0, 16, 32, &bitmap);
+    ok(hr == S_OK, "Failed to create a bitmap, hr %#x.\n", hr);
+    hr = IWICBitmap_GetSize(bitmap, &width, &height);
+    ok(hr == S_OK, "Failed to get bitmap size, hr %#x.\n", hr);
+    ok(width == 3, "Unexpected width %u.\n", width);
+    ok(height == 3, "Unexpected height %u.\n", height);
+    IWICBitmap_Release(bitmap);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 0, 0, 1, 1, &bitmap);
+    ok(hr == S_OK, "Failed to create a bitmap, hr %#x.\n", hr);
+    hr = IWICBitmap_GetSize(bitmap, &width, &height);
+    ok(hr == S_OK, "Failed to get bitmap size, hr %#x.\n", hr);
+    ok(width == 1, "Unexpected width %u.\n", width);
+    ok(height == 1, "Unexpected height %u.\n", height);
+    IWICBitmap_Release(bitmap);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 2, 1, 16, 32, &bitmap);
+    ok(hr == S_OK, "Failed to create a bitmap, hr %#x.\n", hr);
+    hr = IWICBitmap_GetSize(bitmap, &width, &height);
+    ok(hr == S_OK, "Failed to get bitmap size, hr %#x.\n", hr);
+    ok(width == 1, "Unexpected width %u.\n", width);
+    ok(height == 2, "Unexpected height %u.\n", height);
+    IWICBitmap_Release(bitmap);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 0, 0, 0, 2, &bitmap);
+    ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 0, 0, 2, 0, &bitmap);
+    ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 1, 3, 16, 32, &bitmap);
+    ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr);
+
+    hr = IWICImagingFactory_CreateBitmapFromSourceRect(factory, (IWICBitmapSource *)bitmap2, 3, 1, 16, 32, &bitmap);
+    ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr);
+
     IWICBitmap_Release(bitmap2);
 }
 
-- 
2.19.1




More information about the wine-devel mailing list