/*
 * Copyright 2009 Vincent Povirk for CodeWeavers
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include "config.h"

#include <stdarg.h>

#define COBJMACROS

#include "windef.h"
#include "winbase.h"
#include "winreg.h"
#include "objbase.h"
#include "wincodec.h"

#include "wincodecs_private.h"

#include "wine/debug.h"

WINE_DEFAULT_DEBUG_CHANNEL(wincodecs);

typedef struct {
    const IWICImagingFactoryVtbl    *lpIWICImagingFactoryVtbl;
    LONG ref;
} ImagingFactory;

static HRESULT WINAPI ImagingFactory_QueryInterface(IWICImagingFactory *iface, REFIID iid,
    void **ppv)
{
    ImagingFactory *This = (ImagingFactory*)iface;
    TRACE("(%p,%s,%p)\n", iface, debugstr_guid(iid), ppv);

    if (!ppv) return E_INVALIDARG;

    if (IsEqualIID(&IID_IUnknown, iid) || IsEqualIID(&IID_IWICImagingFactory, iid))
    {
        *ppv = This;
    }
    else
    {
        *ppv = NULL;
        return E_NOINTERFACE;
    }

    IUnknown_AddRef((IUnknown*)*ppv);
    return S_OK;
}

static ULONG WINAPI ImagingFactory_AddRef(IWICImagingFactory *iface)
{
    ImagingFactory *This = (ImagingFactory*)iface;
    ULONG ref = InterlockedIncrement(&This->ref);

    TRACE("(%p) refcount=%u\n", iface, ref);

    return ref;
}

static ULONG WINAPI ImagingFactory_Release(IWICImagingFactory *iface)
{
    ImagingFactory *This = (ImagingFactory*)iface;
    ULONG ref = InterlockedDecrement(&This->ref);

    TRACE("(%p) refcount=%u\n", iface, ref);

    if (ref == 0)
        HeapFree(GetProcessHeap(), 0, This);

    return ref;
}

static HRESULT WINAPI ImagingFactory_CreateDecoderFromFilename(
    IWICImagingFactory *iface, LPCWSTR wzFilename, const GUID *pguidVendor,
    DWORD dwDesiredAccess, WICDecodeOptions metadataOptions,
    IWICBitmapDecoder **ppIDecoder)
{
    FIXME("(%p,%s,%s,%u,%u,%p): stub\n", iface, debugstr_w(wzFilename),
        debugstr_guid(pguidVendor), dwDesiredAccess, metadataOptions, ppIDecoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateDecoderFromStream(
    IWICImagingFactory *iface, IStream *pIStream, const GUID *pguidVendor,
    WICDecodeOptions metadataOptions, IWICBitmapDecoder **ppIDecoder)
{
    FIXME("(%p,%p,%s,%u,%p): stub\n", iface, pIStream, debugstr_guid(pguidVendor),
        metadataOptions, ppIDecoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateDecoderFromFileHandle(
    IWICImagingFactory *iface, ULONG_PTR hFile, const GUID *pguidVendor,
    WICDecodeOptions metadataOptions, IWICBitmapDecoder **ppIDecoder)
{
    FIXME("(%p,%lx,%s,%u,%p): stub\n", iface, hFile, debugstr_guid(pguidVendor),
        metadataOptions, ppIDecoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateComponentInfo(IWICImagingFactory *iface,
    REFCLSID clsidComponent, IWICComponentInfo **ppIInfo)
{
    FIXME("(%p,%s,%p): stub\n", iface, debugstr_guid(clsidComponent), ppIInfo);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateDecoder(IWICImagingFactory *iface,
    REFGUID guidContainerFormat, const GUID *pguidVendor,
    IWICBitmapDecoder **ppIDecoder)
{
    FIXME("(%p,%s,%s,%p): stub\n", iface, debugstr_guid(guidContainerFormat),
        debugstr_guid(pguidVendor), ppIDecoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateEncoder(IWICImagingFactory *iface,
    REFGUID guidContainerFormat, const GUID *pguidVendor,
    IWICBitmapEncoder **ppIEncoder)
{
    FIXME("(%p,%s,%s,%p): stub\n", iface, debugstr_guid(guidContainerFormat),
        debugstr_guid(pguidVendor), ppIEncoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreatePalette(IWICImagingFactory *iface,
    IWICPalette **ppIPalette)
{
    TRACE("(%p,%p)\n", iface, ppIPalette);
    return PaletteImpl_Create(ppIPalette);
}

static HRESULT WINAPI ImagingFactory_CreateFormatConverter(IWICImagingFactory *iface,
    IWICFormatConverter **ppIFormatConverter)
{
    FIXME("(%p,%p): stub\n", iface, ppIFormatConverter);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapScaler(IWICImagingFactory *iface,
    IWICBitmapScaler **ppIBitmapScaler)
{
    FIXME("(%p,%p): stub\n", iface, ppIBitmapScaler);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapClipper(IWICImagingFactory *iface,
    IWICBitmapClipper **ppIBitmapClipper)
{
    FIXME("(%p,%p): stub\n", iface, ppIBitmapClipper);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFlipRotator(IWICImagingFactory *iface,
    IWICBitmapFlipRotator **ppIBitmapFlipRotator)
{
    FIXME("(%p,%p): stub\n", iface, ppIBitmapFlipRotator);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateStream(IWICImagingFactory *iface,
    IWICStream **ppIWICStream)
{
    FIXME("(%p,%p): stub\n", iface, ppIWICStream);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateColorContext(IWICImagingFactory *iface,
    IWICColorContext **ppIColorContext)
{
    FIXME("(%p,%p): stub\n", iface, ppIColorContext);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateColorTransformer(IWICImagingFactory *iface,
    IWICColorTransform **ppIColorTransform)
{
    FIXME("(%p,%p): stub\n", iface, ppIColorTransform);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmap(IWICImagingFactory *iface,
    UINT uiWidth, UINT uiHeight, REFWICPixelFormatGUID pixelFormat,
    WICBitmapCreateCacheOption option, IWICBitmap **ppIBitmap)
{
    FIXME("(%p,%u,%u,%s,%u,%p): stub\n", iface, uiWidth, uiHeight,
        debugstr_guid(pixelFormat), option, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFromSource(IWICImagingFactory *iface,
    IWICBitmapSource *piBitmapSource, WICBitmapCreateCacheOption option,
    IWICBitmap **ppIBitmap)
{
    FIXME("(%p,%p,%u,%p): stub\n", iface, piBitmapSource, option, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFromSourceRect(IWICImagingFactory *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,
        height, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFromMemory(IWICImagingFactory *iface,
    UINT uiWidth, UINT uiHeight, REFWICPixelFormatGUID pixelFormat, UINT cbStride,
    UINT cbBufferSize, BYTE *pbBuffer, IWICBitmap **ppIBitmap)
{
    FIXME("(%p,%u,%u,%s,%u,%u,%p,%p): stub\n", iface, uiWidth, uiHeight,
        debugstr_guid(pixelFormat), cbStride, cbBufferSize, pbBuffer, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFromHBITMAP(IWICImagingFactory *iface,
    HBITMAP hBitmap, HPALETTE hPalette, WICBitmapAlphaChannelOption options,
    IWICBitmap **ppIBitmap)
{
    FIXME("(%p,%p,%p,%u,%p): stub\n", iface, hBitmap, hPalette, options, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateBitmapFromHICON(IWICImagingFactory *iface,
    HICON hIcon, IWICBitmap **ppIBitmap)
{
    FIXME("(%p,%p,%p): stub\n", iface, hIcon, ppIBitmap);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateComponentEnumerator(IWICImagingFactory *iface,
    DWORD componentTypes, DWORD options, IEnumUnknown **ppIEnumUnknown)
{
    FIXME("(%p,%u,%u,%p): stub\n", iface, componentTypes, options, ppIEnumUnknown);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateFastMetadataEncoderFromDecoder(
    IWICImagingFactory *iface, IWICBitmapDecoder *pIDecoder,
    IWICFastMetadataEncoder **ppIFastEncoder)
{
    FIXME("(%p,%p,%p): stub\n", iface, pIDecoder, ppIFastEncoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateFastMetadataEncoderFromFrameDecode(
    IWICImagingFactory *iface, IWICBitmapFrameDecode *pIFrameDecoder,
    IWICFastMetadataEncoder **ppIFastEncoder)
{
    FIXME("(%p,%p,%p): stub\n", iface, pIFrameDecoder, ppIFastEncoder);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateQueryWriter(IWICImagingFactory *iface,
    REFGUID guidMetadataFormat, const GUID *pguidVendor,
    IWICMetadataQueryWriter **ppIQueryWriter)
{
    FIXME("(%p,%s,%s,%p): stub\n", iface, debugstr_guid(guidMetadataFormat),
        debugstr_guid(pguidVendor), ppIQueryWriter);
    return E_NOTIMPL;
}

static HRESULT WINAPI ImagingFactory_CreateQueryWriterFromReader(IWICImagingFactory *iface,
    IWICMetadataQueryReader *pIQueryReader, const GUID *pguidVendor,
    IWICMetadataQueryWriter **ppIQueryWriter)
{
    FIXME("(%p,%p,%s,%p): stub\n", iface, pIQueryReader, debugstr_guid(pguidVendor),
        ppIQueryWriter);
    return E_NOTIMPL;
}

static const IWICImagingFactoryVtbl ImagingFactory_Vtbl = {
    ImagingFactory_QueryInterface,
    ImagingFactory_AddRef,
    ImagingFactory_Release,
    ImagingFactory_CreateDecoderFromFilename,
    ImagingFactory_CreateDecoderFromStream,
    ImagingFactory_CreateDecoderFromFileHandle,
    ImagingFactory_CreateComponentInfo,
    ImagingFactory_CreateDecoder,
    ImagingFactory_CreateEncoder,
    ImagingFactory_CreatePalette,
    ImagingFactory_CreateFormatConverter,
    ImagingFactory_CreateBitmapScaler,
    ImagingFactory_CreateBitmapClipper,
    ImagingFactory_CreateBitmapFlipRotator,
    ImagingFactory_CreateStream,
    ImagingFactory_CreateColorContext,
    ImagingFactory_CreateColorTransformer,
    ImagingFactory_CreateBitmap,
    ImagingFactory_CreateBitmapFromSource,
    ImagingFactory_CreateBitmapFromSourceRect,
    ImagingFactory_CreateBitmapFromMemory,
    ImagingFactory_CreateBitmapFromHBITMAP,
    ImagingFactory_CreateBitmapFromHICON,
    ImagingFactory_CreateComponentEnumerator,
    ImagingFactory_CreateFastMetadataEncoderFromDecoder,
    ImagingFactory_CreateFastMetadataEncoderFromFrameDecode,
    ImagingFactory_CreateQueryWriter,
    ImagingFactory_CreateQueryWriterFromReader
};

HRESULT ImagingFactory_CreateInstance(IUnknown *pUnkOuter, REFIID iid, void** ppv)
{
    ImagingFactory *This;
    HRESULT ret;

    TRACE("(%p,%s,%p)\n", pUnkOuter, debugstr_guid(iid), ppv);

    *ppv = NULL;

    if (pUnkOuter) return CLASS_E_NOAGGREGATION;

    This = HeapAlloc(GetProcessHeap(), 0, sizeof(ImagingFactory));
    if (!This) return E_OUTOFMEMORY;

    This->lpIWICImagingFactoryVtbl = &ImagingFactory_Vtbl;
    This->ref = 1;

    ret = IUnknown_QueryInterface((IUnknown*)This, iid, ppv);
    IUnknown_Release((IUnknown*)This);

    return ret;
}
