From 30f98340618b1ebfce38c83ac7c189a34d2559e4 Mon Sep 17 00:00:00 2001 From: Vincent Povirk Date: Fri, 13 Jun 2014 14:02:23 -0500 Subject: [PATCH] windowscodecs: Share WriteSource code between implementations. --- dlls/windowscodecs/bmpencode.c | 59 +++--------------- dlls/windowscodecs/icnsformat.c | 58 +++-------------- dlls/windowscodecs/jpegformat.c | 62 ++----------------- dlls/windowscodecs/main.c | 86 ++++++++++++++++++++++++++ dlls/windowscodecs/pngformat.c | 62 ++----------------- dlls/windowscodecs/tiffformat.c | 64 +++---------------- dlls/windowscodecs/wincodecs_private.h | 10 +++ 7 files changed, 131 insertions(+), 270 deletions(-) diff --git a/dlls/windowscodecs/bmpencode.c b/dlls/windowscodecs/bmpencode.c index 715b8f6691e..a570884a77b 100644 --- a/dlls/windowscodecs/bmpencode.c +++ b/dlls/windowscodecs/bmpencode.c @@ -260,63 +260,22 @@ static HRESULT WINAPI BmpFrameEncode_WriteSource(IWICBitmapFrameEncode *iface, { BmpFrameEncode *This = impl_from_IWICBitmapFrameEncode(iface); HRESULT hr; - WICRect rc; - WICPixelFormatGUID guid; TRACE("(%p,%p,%p)\n", iface, pIBitmapSource, prc); - if (!This->initialized || !This->width || !This->height) + if (!This->initialized) return WINCODEC_ERR_WRONGSTATE; - if (!This->format) + hr = configure_write_source(iface, pIBitmapSource, prc, + This->format ? This->format->guid : NULL, This->width, This->height, + This->xres, This->yres); + + if (SUCCEEDED(hr)) { - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - hr = BmpFrameEncode_SetPixelFormat(iface, &guid); - if (FAILED(hr)) return hr; + hr = write_source(iface, pIBitmapSource, prc, + This->format->guid, This->format->bpp, This->width, This->height); } - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - if (memcmp(&guid, This->format->guid, sizeof(GUID)) != 0) - { - /* should use WICConvertBitmapSource to convert, but that's unimplemented */ - ERR("format %s unsupported\n", debugstr_guid(&guid)); - return E_FAIL; - } - - if (This->xres == 0.0 || This->yres == 0.0) - { - double xres, yres; - hr = IWICBitmapSource_GetResolution(pIBitmapSource, &xres, &yres); - if (FAILED(hr)) return hr; - hr = BmpFrameEncode_SetResolution(iface, xres, yres); - if (FAILED(hr)) return hr; - } - - if (!prc) - { - UINT width, height; - hr = IWICBitmapSource_GetSize(pIBitmapSource, &width, &height); - if (FAILED(hr)) return hr; - rc.X = 0; - rc.Y = 0; - rc.Width = width; - rc.Height = height; - prc = &rc; - } - - if (prc->Width != This->width) return E_INVALIDARG; - - hr = BmpFrameEncode_AllocateBits(This); - if (FAILED(hr)) return hr; - - hr = IWICBitmapSource_CopyPixels(pIBitmapSource, prc, This->stride, - This->stride*(This->height-This->lineswritten), - This->bits + This->stride*This->lineswritten); - - This->lineswritten += prc->Height; - - return S_OK; + return hr; } static HRESULT WINAPI BmpFrameEncode_Commit(IWICBitmapFrameEncode *iface) diff --git a/dlls/windowscodecs/icnsformat.c b/dlls/windowscodecs/icnsformat.c index aa14189ba65..d5d123a7625 100644 --- a/dlls/windowscodecs/icnsformat.c +++ b/dlls/windowscodecs/icnsformat.c @@ -391,66 +391,22 @@ static HRESULT WINAPI IcnsFrameEncode_WriteSource(IWICBitmapFrameEncode *iface, { IcnsFrameEncode *This = impl_from_IWICBitmapFrameEncode(iface); HRESULT hr; - WICRect rc; - WICPixelFormatGUID guid; - UINT stride; - BYTE *pixeldata = NULL; TRACE("(%p,%p,%p)\n", iface, pIBitmapSource, prc); - if (!This->initialized || !This->size) - { - hr = WINCODEC_ERR_WRONGSTATE; - goto end; - } + if (!This->initialized) + return WINCODEC_ERR_WRONGSTATE; - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) - goto end; - if (!IsEqualGUID(&guid, &GUID_WICPixelFormat32bppBGRA)) - { - FIXME("format %s unsupported, could use WICConvertBitmapSource to convert\n", debugstr_guid(&guid)); - hr = E_FAIL; - goto end; - } + hr = configure_write_source(iface, pIBitmapSource, &prc, + &GUID_WICPixelFormat32bppBGRA, This->size, This->size, + 1.0, 1.0); - if (!prc) - { - UINT width, height; - hr = IWICBitmapSource_GetSize(pIBitmapSource, &width, &height); - if (FAILED(hr)) - goto end; - rc.X = 0; - rc.Y = 0; - rc.Width = width; - rc.Height = height; - prc = &rc; - } - - if (prc->Width != This->size) - { - hr = E_INVALIDARG; - goto end; - } - - stride = (32 * This->size + 7)/8; - pixeldata = HeapAlloc(GetProcessHeap(), 0, stride * prc->Height); - if (!pixeldata) - { - hr = E_OUTOFMEMORY; - goto end; - } - - hr = IWICBitmapSource_CopyPixels(pIBitmapSource, prc, stride, - stride*prc->Height, pixeldata); if (SUCCEEDED(hr)) { - hr = IWICBitmapFrameEncode_WritePixels(iface, prc->Height, stride, - stride*prc->Height, pixeldata); + hr = write_source(iface, pIBitmapSource, prc, + &GUID_WICPixelFormat32bppBGRA, 32, This->size, This->size); } -end: - HeapFree(GetProcessHeap(), 0, pixeldata); return hr; } diff --git a/dlls/windowscodecs/jpegformat.c b/dlls/windowscodecs/jpegformat.c index 05f65389d2e..e29996d8a3a 100644 --- a/dlls/windowscodecs/jpegformat.c +++ b/dlls/windowscodecs/jpegformat.c @@ -1107,71 +1107,21 @@ static HRESULT WINAPI JpegEncoder_Frame_WriteSource(IWICBitmapFrameEncode *iface { JpegEncoder *This = impl_from_IWICBitmapFrameEncode(iface); HRESULT hr; - WICRect rc; - WICPixelFormatGUID guid; - UINT stride; - BYTE *pixeldata; TRACE("(%p,%p,%p)\n", iface, pIBitmapSource, prc); - if (!This->frame_initialized || !This->width || !This->height) + if (!This->frame_initialized) return WINCODEC_ERR_WRONGSTATE; - if (!This->format) - { - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetPixelFormat(iface, &guid); - if (FAILED(hr)) return hr; - } - - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - if (memcmp(&guid, This->format->guid, sizeof(GUID)) != 0) - { - /* FIXME: should use WICConvertBitmapSource to convert */ - ERR("format %s unsupported\n", debugstr_guid(&guid)); - return E_FAIL; - } - - if (This->xres == 0.0 || This->yres == 0.0) - { - double xres, yres; - hr = IWICBitmapSource_GetResolution(pIBitmapSource, &xres, &yres); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetResolution(iface, xres, yres); - if (FAILED(hr)) return hr; - } - - if (!prc) - { - UINT width, height; - hr = IWICBitmapSource_GetSize(pIBitmapSource, &width, &height); - if (FAILED(hr)) return hr; - rc.X = 0; - rc.Y = 0; - rc.Width = width; - rc.Height = height; - prc = &rc; - } - - if (prc->Width != This->width) return E_INVALIDARG; - - stride = (This->format->bpp * This->width + 7)/8; - - pixeldata = HeapAlloc(GetProcessHeap(), 0, stride * prc->Height); - if (!pixeldata) return E_OUTOFMEMORY; - - hr = IWICBitmapSource_CopyPixels(pIBitmapSource, prc, stride, - stride*prc->Height, pixeldata); + hr = configure_write_source(iface, pIBitmapSource, prc, + This->format ? This->format->guid : NULL, This->width, This->height, + This->xres, This->yres); if (SUCCEEDED(hr)) { - hr = IWICBitmapFrameEncode_WritePixels(iface, prc->Height, stride, - stride*prc->Height, pixeldata); + hr = write_source(iface, pIBitmapSource, prc, + This->format->guid, This->format->bpp, This->width, This->height); } - HeapFree(GetProcessHeap(), 0, pixeldata); - return hr; } diff --git a/dlls/windowscodecs/main.c b/dlls/windowscodecs/main.c index 8efaee654aa..a4cb93fe315 100644 --- a/dlls/windowscodecs/main.c +++ b/dlls/windowscodecs/main.c @@ -118,6 +118,92 @@ HRESULT copy_pixels(UINT bpp, const BYTE *srcbuffer, } } +HRESULT configure_write_source(IWICBitmapFrameEncode *iface, + IWICBitmapSource *source, const WICRect *prc, + const WICPixelFormatGUID *format, + INT width, INT height, double xres, double yres) +{ + HRESULT hr=S_OK; + WICPixelFormatGUID src_format, dst_format; + + if (width == 0 || height == 0) + return WINCODEC_ERR_WRONGSTATE; + + hr = IWICBitmapSource_GetPixelFormat(source, &src_format); + if (FAILED(hr)) return hr; + + if (!format) + { + dst_format = src_format; + + hr = IWICBitmapFrameEncode_SetPixelFormat(iface, &dst_format); + if (FAILED(hr)) return hr; + + format = &dst_format; + } + + if (!IsEqualGUID(&src_format, format)) + { + /* FIXME: should use WICConvertBitmapSource to convert */ + ERR("format %s unsupported\n", debugstr_guid(&src_format)); + return E_FAIL; + } + + if (xres == 0.0 || yres == 0.0) + { + hr = IWICBitmapSource_GetResolution(source, &xres, &yres); + if (FAILED(hr)) return hr; + hr = IWICBitmapFrameEncode_SetResolution(iface, xres, yres); + if (FAILED(hr)) return hr; + } + + return hr; +} + +HRESULT write_source(IWICBitmapFrameEncode *iface, + IWICBitmapSource *source, const WICRect *prc, + const WICPixelFormatGUID *format, UINT bpp, + INT width, INT height) +{ + HRESULT hr=S_OK; + WICRect rc; + UINT stride; + BYTE* pixeldata; + + if (!prc) + { + UINT src_width, src_height; + hr = IWICBitmapSource_GetSize(source, &src_width, &src_height); + if (FAILED(hr)) return hr; + rc.X = 0; + rc.Y = 0; + rc.Width = src_width; + rc.Height = src_height; + prc = &rc; + } + + if (prc->Width != width) + return E_INVALIDARG; + + stride = (bpp * width + 7)/8; + + pixeldata = HeapAlloc(GetProcessHeap(), 0, stride * prc->Height); + if (!pixeldata) return E_OUTOFMEMORY; + + hr = IWICBitmapSource_CopyPixels(source, prc, stride, + stride*prc->Height, pixeldata); + + if (SUCCEEDED(hr)) + { + hr = IWICBitmapFrameEncode_WritePixels(iface, prc->Height, stride, + stride*prc->Height, pixeldata); + } + + HeapFree(GetProcessHeap(), 0, pixeldata); + + return hr; +} + void reverse_bgr8(UINT bytesperpixel, LPBYTE bits, UINT width, UINT height, INT stride) { UINT x, y; diff --git a/dlls/windowscodecs/pngformat.c b/dlls/windowscodecs/pngformat.c index 579989b5337..bd5cd3d0376 100644 --- a/dlls/windowscodecs/pngformat.c +++ b/dlls/windowscodecs/pngformat.c @@ -1304,71 +1304,21 @@ static HRESULT WINAPI PngFrameEncode_WriteSource(IWICBitmapFrameEncode *iface, { PngEncoder *This = impl_from_IWICBitmapFrameEncode(iface); HRESULT hr; - WICRect rc; - WICPixelFormatGUID guid; - UINT stride; - BYTE *pixeldata; TRACE("(%p,%p,%p)\n", iface, pIBitmapSource, prc); - if (!This->frame_initialized || !This->width || !This->height) + if (!This->frame_initialized) return WINCODEC_ERR_WRONGSTATE; - if (!This->format) - { - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetPixelFormat(iface, &guid); - if (FAILED(hr)) return hr; - } - - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - if (memcmp(&guid, This->format->guid, sizeof(GUID)) != 0) - { - /* FIXME: should use WICConvertBitmapSource to convert */ - ERR("format %s unsupported\n", debugstr_guid(&guid)); - return E_FAIL; - } - - if (This->xres == 0.0 || This->yres == 0.0) - { - double xres, yres; - hr = IWICBitmapSource_GetResolution(pIBitmapSource, &xres, &yres); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetResolution(iface, xres, yres); - if (FAILED(hr)) return hr; - } - - if (!prc) - { - UINT width, height; - hr = IWICBitmapSource_GetSize(pIBitmapSource, &width, &height); - if (FAILED(hr)) return hr; - rc.X = 0; - rc.Y = 0; - rc.Width = width; - rc.Height = height; - prc = &rc; - } - - if (prc->Width != This->width) return E_INVALIDARG; - - stride = (This->format->bpp * This->width + 7)/8; - - pixeldata = HeapAlloc(GetProcessHeap(), 0, stride * prc->Height); - if (!pixeldata) return E_OUTOFMEMORY; - - hr = IWICBitmapSource_CopyPixels(pIBitmapSource, prc, stride, - stride*prc->Height, pixeldata); + hr = configure_write_source(iface, pIBitmapSource, prc, + This->format ? This->format->guid : NULL, This->width, This->height, + This->xres, This->yres); if (SUCCEEDED(hr)) { - hr = IWICBitmapFrameEncode_WritePixels(iface, prc->Height, stride, - stride*prc->Height, pixeldata); + hr = write_source(iface, pIBitmapSource, prc, + This->format->guid, This->format->bpp, This->width, This->height); } - HeapFree(GetProcessHeap(), 0, pixeldata); - return hr; } diff --git a/dlls/windowscodecs/tiffformat.c b/dlls/windowscodecs/tiffformat.c index c2c288e3243..74a73bcb7ec 100644 --- a/dlls/windowscodecs/tiffformat.c +++ b/dlls/windowscodecs/tiffformat.c @@ -1653,73 +1653,23 @@ static HRESULT WINAPI TiffFrameEncode_WriteSource(IWICBitmapFrameEncode *iface, { TiffFrameEncode *This = impl_from_IWICBitmapFrameEncode(iface); HRESULT hr; - WICRect rc; - WICPixelFormatGUID guid; - UINT stride; - BYTE *pixeldata; TRACE("(%p,%p,%p)\n", iface, pIBitmapSource, prc); - if (!This->initialized || !This->width || !This->height) + if (!This->initialized) return WINCODEC_ERR_WRONGSTATE; - if (!This->format) - { - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetPixelFormat(iface, &guid); - if (FAILED(hr)) return hr; - } - - hr = IWICBitmapSource_GetPixelFormat(pIBitmapSource, &guid); - if (FAILED(hr)) return hr; - if (memcmp(&guid, This->format->guid, sizeof(GUID)) != 0) - { - /* FIXME: should use WICConvertBitmapSource to convert */ - ERR("format %s unsupported\n", debugstr_guid(&guid)); - return E_FAIL; - } - - if (This->xres == 0.0 || This->yres == 0.0) - { - double xres, yres; - hr = IWICBitmapSource_GetResolution(pIBitmapSource, &xres, &yres); - if (FAILED(hr)) return hr; - hr = IWICBitmapFrameEncode_SetResolution(iface, xres, yres); - if (FAILED(hr)) return hr; - } - - if (!prc) - { - UINT width, height; - hr = IWICBitmapSource_GetSize(pIBitmapSource, &width, &height); - if (FAILED(hr)) return hr; - rc.X = 0; - rc.Y = 0; - rc.Width = width; - rc.Height = height; - prc = &rc; - } - - if (prc->Width != This->width) return E_INVALIDARG; - - stride = (This->format->bpp * This->width + 7)/8; - - pixeldata = HeapAlloc(GetProcessHeap(), 0, stride * prc->Height); - if (!pixeldata) return E_OUTOFMEMORY; - - hr = IWICBitmapSource_CopyPixels(pIBitmapSource, prc, stride, - stride*prc->Height, pixeldata); + hr = configure_write_source(iface, pIBitmapSource, prc, + This->format ? This->format->guid : NULL, This->width, This->height, + This->xres, This->yres); if (SUCCEEDED(hr)) { - hr = IWICBitmapFrameEncode_WritePixels(iface, prc->Height, stride, - stride*prc->Height, pixeldata); + hr = write_source(iface, pIBitmapSource, prc, + This->format->guid, This->format->bpp, This->width, This->height); } - HeapFree(GetProcessHeap(), 0, pixeldata); - - return S_OK; + return hr; } static HRESULT WINAPI TiffFrameEncode_Commit(IWICBitmapFrameEncode *iface) diff --git a/dlls/windowscodecs/wincodecs_private.h b/dlls/windowscodecs/wincodecs_private.h index 1a4c97f3b1d..fbbc34fa86d 100644 --- a/dlls/windowscodecs/wincodecs_private.h +++ b/dlls/windowscodecs/wincodecs_private.h @@ -99,6 +99,16 @@ extern HRESULT copy_pixels(UINT bpp, const BYTE *srcbuffer, UINT srcwidth, UINT srcheight, INT srcstride, const WICRect *rc, UINT dststride, UINT dstbuffersize, BYTE *dstbuffer) DECLSPEC_HIDDEN; +extern HRESULT configure_write_source(IWICBitmapFrameEncode *iface, + IWICBitmapSource *source, const WICRect *prc, + const WICPixelFormatGUID *format, + INT width, INT height, double xres, double yres) DECLSPEC_HIDDEN; + +extern HRESULT write_source(IWICBitmapFrameEncode *iface, + IWICBitmapSource *source, const WICRect *prc, + const WICPixelFormatGUID *format, UINT bpp, + INT width, INT height) DECLSPEC_HIDDEN; + extern void reverse_bgr8(UINT bytesperpixel, LPBYTE bits, UINT width, UINT height, INT stride) DECLSPEC_HIDDEN; extern HRESULT get_pixelformat_bpp(const GUID *pixelformat, UINT *bpp) DECLSPEC_HIDDEN;