| Index: src/ports/SkImageDecoder_WIC.cpp
|
| diff --git a/src/ports/SkImageDecoder_WIC.cpp b/src/ports/SkImageDecoder_WIC.cpp
|
| index c7222e635a993f97f5e07ee0bc140f64b1864f5b..ef6de00dc93335bbbb967711eb53cc0f02fb729d 100644
|
| --- a/src/ports/SkImageDecoder_WIC.cpp
|
| +++ b/src/ports/SkImageDecoder_WIC.cpp
|
| @@ -31,7 +31,6 @@
|
|
|
| #include <wincodec.h>
|
| #include "SkAutoCoInitialize.h"
|
| -#include "SkImageDecoder.h"
|
| #include "SkImageEncoder.h"
|
| #include "SkIStream.h"
|
| #include "SkMovie.h"
|
| @@ -48,222 +47,6 @@
|
| #undef CLSID_WICImagingFactory
|
| #endif
|
|
|
| -class SkImageDecoder_WIC : public SkImageDecoder {
|
| -public:
|
| - // Decoding modes corresponding to SkImageDecoder::Mode, plus an extra mode for decoding
|
| - // only the format.
|
| - enum WICModes {
|
| - kDecodeFormat_WICMode,
|
| - kDecodeBounds_WICMode,
|
| - kDecodePixels_WICMode,
|
| - };
|
| -
|
| - /**
|
| - * Helper function to decode an SkStream.
|
| - * @param stream SkStream to decode. Must be at the beginning.
|
| - * @param bm SkBitmap to decode into. Only used if wicMode is kDecodeBounds_WICMode or
|
| - * kDecodePixels_WICMode, in which case it must not be nullptr.
|
| - * @param format Out parameter for the SkImageDecoder::Format of the SkStream. Only used if
|
| - * wicMode is kDecodeFormat_WICMode.
|
| - */
|
| - bool decodeStream(SkStream* stream, SkBitmap* bm, WICModes wicMode, Format* format) const;
|
| -
|
| -protected:
|
| - Result onDecode(SkStream* stream, SkBitmap* bm, Mode mode) override;
|
| -};
|
| -
|
| -struct FormatConversion {
|
| - GUID fGuidFormat;
|
| - SkImageDecoder::Format fFormat;
|
| -};
|
| -
|
| -static const FormatConversion gFormatConversions[] = {
|
| - { GUID_ContainerFormatBmp, SkImageDecoder::kBMP_Format },
|
| - { GUID_ContainerFormatGif, SkImageDecoder::kGIF_Format },
|
| - { GUID_ContainerFormatIco, SkImageDecoder::kICO_Format },
|
| - { GUID_ContainerFormatJpeg, SkImageDecoder::kJPEG_Format },
|
| - { GUID_ContainerFormatPng, SkImageDecoder::kPNG_Format },
|
| -};
|
| -
|
| -static SkImageDecoder::Format GuidContainerFormat_to_Format(REFGUID guid) {
|
| - for (size_t i = 0; i < SK_ARRAY_COUNT(gFormatConversions); i++) {
|
| - if (IsEqualGUID(guid, gFormatConversions[i].fGuidFormat)) {
|
| - return gFormatConversions[i].fFormat;
|
| - }
|
| - }
|
| - return SkImageDecoder::kUnknown_Format;
|
| -}
|
| -
|
| -SkImageDecoder::Result SkImageDecoder_WIC::onDecode(SkStream* stream, SkBitmap* bm, Mode mode) {
|
| - WICModes wicMode;
|
| - switch (mode) {
|
| - case SkImageDecoder::kDecodeBounds_Mode:
|
| - wicMode = kDecodeBounds_WICMode;
|
| - break;
|
| - case SkImageDecoder::kDecodePixels_Mode:
|
| - wicMode = kDecodePixels_WICMode;
|
| - break;
|
| - }
|
| - return this->decodeStream(stream, bm, wicMode, nullptr) ? kSuccess : kFailure;
|
| -}
|
| -
|
| -bool SkImageDecoder_WIC::decodeStream(SkStream* stream, SkBitmap* bm, WICModes wicMode,
|
| - Format* format) const {
|
| - //Initialize COM.
|
| - SkAutoCoInitialize scopedCo;
|
| - if (!scopedCo.succeeded()) {
|
| - return false;
|
| - }
|
| -
|
| - HRESULT hr = S_OK;
|
| -
|
| - //Create Windows Imaging Component ImagingFactory.
|
| - SkTScopedComPtr<IWICImagingFactory> piImagingFactory;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = CoCreateInstance(
|
| - CLSID_WICImagingFactory
|
| - , nullptr
|
| - , CLSCTX_INPROC_SERVER
|
| - , IID_PPV_ARGS(&piImagingFactory)
|
| - );
|
| - }
|
| -
|
| - //Convert SkStream to IStream.
|
| - SkTScopedComPtr<IStream> piStream;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = SkIStream::CreateFromSkStream(stream, false, &piStream);
|
| - }
|
| -
|
| - //Make sure we're at the beginning of the stream.
|
| - if (SUCCEEDED(hr)) {
|
| - LARGE_INTEGER liBeginning = { 0 };
|
| - hr = piStream->Seek(liBeginning, STREAM_SEEK_SET, nullptr);
|
| - }
|
| -
|
| - //Create the decoder from the stream content.
|
| - SkTScopedComPtr<IWICBitmapDecoder> piBitmapDecoder;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piImagingFactory->CreateDecoderFromStream(
|
| - piStream.get() //Image to be decoded
|
| - , nullptr //No particular vendor
|
| - , WICDecodeMetadataCacheOnDemand //Cache metadata when needed
|
| - , &piBitmapDecoder //Pointer to the decoder
|
| - );
|
| - }
|
| -
|
| - if (kDecodeFormat_WICMode == wicMode) {
|
| - SkASSERT(format != nullptr);
|
| - //Get the format
|
| - if (SUCCEEDED(hr)) {
|
| - GUID guidFormat;
|
| - hr = piBitmapDecoder->GetContainerFormat(&guidFormat);
|
| - if (SUCCEEDED(hr)) {
|
| - *format = GuidContainerFormat_to_Format(guidFormat);
|
| - return true;
|
| - }
|
| - }
|
| - return false;
|
| - }
|
| -
|
| - //Get the first frame from the decoder.
|
| - SkTScopedComPtr<IWICBitmapFrameDecode> piBitmapFrameDecode;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piBitmapDecoder->GetFrame(0, &piBitmapFrameDecode);
|
| - }
|
| -
|
| - //Get the BitmapSource interface of the frame.
|
| - SkTScopedComPtr<IWICBitmapSource> piBitmapSourceOriginal;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piBitmapFrameDecode->QueryInterface(
|
| - IID_PPV_ARGS(&piBitmapSourceOriginal)
|
| - );
|
| - }
|
| -
|
| - //Get the size of the bitmap.
|
| - UINT width;
|
| - UINT height;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piBitmapSourceOriginal->GetSize(&width, &height);
|
| - }
|
| -
|
| - //Exit early if we're only looking for the bitmap bounds.
|
| - if (SUCCEEDED(hr)) {
|
| - bm->setInfo(SkImageInfo::MakeN32Premul(width, height));
|
| - if (kDecodeBounds_WICMode == wicMode) {
|
| - return true;
|
| - }
|
| - if (!this->allocPixelRef(bm, nullptr)) {
|
| - return false;
|
| - }
|
| - }
|
| -
|
| - //Create a format converter.
|
| - SkTScopedComPtr<IWICFormatConverter> piFormatConverter;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piImagingFactory->CreateFormatConverter(&piFormatConverter);
|
| - }
|
| -
|
| - GUID destinationPixelFormat;
|
| - if (this->getRequireUnpremultipliedColors()) {
|
| - destinationPixelFormat = GUID_WICPixelFormat32bppBGRA;
|
| - } else {
|
| - destinationPixelFormat = GUID_WICPixelFormat32bppPBGRA;
|
| - }
|
| -
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piFormatConverter->Initialize(
|
| - piBitmapSourceOriginal.get() //Input bitmap to convert
|
| - , destinationPixelFormat //Destination pixel format
|
| - , WICBitmapDitherTypeNone //Specified dither patterm
|
| - , nullptr //Specify a particular palette
|
| - , 0.f //Alpha threshold
|
| - , WICBitmapPaletteTypeCustom //Palette translation type
|
| - );
|
| - }
|
| -
|
| - //Get the BitmapSource interface of the format converter.
|
| - SkTScopedComPtr<IWICBitmapSource> piBitmapSourceConverted;
|
| - if (SUCCEEDED(hr)) {
|
| - hr = piFormatConverter->QueryInterface(
|
| - IID_PPV_ARGS(&piBitmapSourceConverted)
|
| - );
|
| - }
|
| -
|
| - //Copy the pixels into the bitmap.
|
| - if (SUCCEEDED(hr)) {
|
| - SkAutoLockPixels alp(*bm);
|
| - bm->eraseColor(SK_ColorTRANSPARENT);
|
| - const UINT stride = (UINT) bm->rowBytes();
|
| - hr = piBitmapSourceConverted->CopyPixels(
|
| - nullptr, //Get all the pixels
|
| - stride,
|
| - stride * height,
|
| - reinterpret_cast<BYTE *>(bm->getPixels())
|
| - );
|
| -
|
| - // Note: we don't need to premultiply here since we specified PBGRA
|
| - if (SkBitmap::ComputeIsOpaque(*bm)) {
|
| - bm->setAlphaType(kOpaque_SkAlphaType);
|
| - }
|
| - }
|
| -
|
| - return SUCCEEDED(hr);
|
| -}
|
| -
|
| -/////////////////////////////////////////////////////////////////////////
|
| -
|
| -extern SkImageDecoder* image_decoder_from_stream(SkStreamRewindable*);
|
| -
|
| -SkImageDecoder* SkImageDecoder::Factory(SkStreamRewindable* stream) {
|
| - SkImageDecoder* decoder = image_decoder_from_stream(stream);
|
| - if (nullptr == decoder) {
|
| - // If no image decoder specific to the stream exists, use SkImageDecoder_WIC.
|
| - return new SkImageDecoder_WIC;
|
| - } else {
|
| - return decoder;
|
| - }
|
| -}
|
| -
|
| /////////////////////////////////////////////////////////////////////////
|
|
|
| SkMovie* SkMovie::DecodeStream(SkStreamRewindable* stream) {
|
| @@ -275,6 +58,10 @@ SkMovie* SkMovie::DecodeStream(SkStreamRewindable* stream) {
|
| class SkImageEncoder_WIC : public SkImageEncoder {
|
| public:
|
| SkImageEncoder_WIC(Type t) : fType(t) {}
|
| +
|
| + // DO NOT USE this constructor. This exists only so SkForceLinking can
|
| + // link the WIC image encoder.
|
| + SkImageEncoder_WIC() {}
|
|
|
| protected:
|
| virtual bool onEncode(SkWStream* stream, const SkBitmap& bm, int quality);
|
| @@ -451,15 +238,6 @@ static SkImageEncoder* sk_imageencoder_wic_factory(SkImageEncoder::Type t) {
|
|
|
| static SkImageEncoder_EncodeReg gEReg(sk_imageencoder_wic_factory);
|
|
|
| -static SkImageDecoder::Format get_format_wic(SkStreamRewindable* stream) {
|
| - SkImageDecoder::Format format;
|
| - SkImageDecoder_WIC codec;
|
| - if (!codec.decodeStream(stream, nullptr, SkImageDecoder_WIC::kDecodeFormat_WICMode, &format)) {
|
| - format = SkImageDecoder::kUnknown_Format;
|
| - }
|
| - return format;
|
| -}
|
| -
|
| -static SkImageDecoder_FormatReg gFormatReg(get_format_wic);
|
| +DEFINE_ENCODER_CREATOR(ImageEncoder_WIC);
|
|
|
| #endif // defined(SK_BUILD_FOR_WIN32)
|
|
|