diff --git a/src/effects/SkToSRGBColorFilter.cpp b/src/effects/SkToSRGBColorFilter.cpp index b24ca8dcc8..4b5558da76 100644 --- a/src/effects/SkToSRGBColorFilter.cpp +++ b/src/effects/SkToSRGBColorFilter.cpp @@ -53,6 +53,6 @@ void SkToSRGBColorFilter::flatten(SkWriteBuffer& buffer) const { std::unique_ptr SkToSRGBColorFilter::asFragmentProcessor( GrContext*, const GrColorSpaceInfo&) const { return GrColorSpaceXformEffect::Make(fSrcColorSpace.get(), kPremul_SkAlphaType, - sk_srgb_singleton(), kPremul_SkAlphaType); + sk_srgb_singleton()); } #endif diff --git a/src/gpu/GrColorSpaceXform.cpp b/src/gpu/GrColorSpaceXform.cpp index fdcc0cde82..f7b924a641 100644 --- a/src/gpu/GrColorSpaceXform.cpp +++ b/src/gpu/GrColorSpaceXform.cpp @@ -144,10 +144,9 @@ GrFragmentProcessor::OptimizationFlags GrColorSpaceXformEffect::OptFlags( std::unique_ptr GrColorSpaceXformEffect::Make(SkColorSpace* src, SkAlphaType srcAT, - SkColorSpace* dst, - SkAlphaType dstAT) { + SkColorSpace* dst) { auto xform = GrColorSpaceXform::Make(src, srcAT, - dst, dstAT); + dst, kPremul_SkAlphaType); if (!xform) { return nullptr; } diff --git a/src/gpu/GrColorSpaceXform.h b/src/gpu/GrColorSpaceXform.h index 4542d5cb72..d824dcd55b 100644 --- a/src/gpu/GrColorSpaceXform.h +++ b/src/gpu/GrColorSpaceXform.h @@ -52,7 +52,7 @@ public: * Returns a fragment processor that converts the input's color space from src to dst. */ static std::unique_ptr Make(SkColorSpace* src, SkAlphaType srcAT, - SkColorSpace* dst, SkAlphaType dstAT); + SkColorSpace* dst); /** * Returns a fragment processor that calls the passed in fragment processor, and then converts diff --git a/src/gpu/GrYUVProvider.cpp b/src/gpu/GrYUVProvider.cpp index f5bc7ea6e8..a5b71dd651 100644 --- a/src/gpu/GrYUVProvider.cpp +++ b/src/gpu/GrYUVProvider.cpp @@ -141,8 +141,7 @@ sk_sp GrYUVProvider::refAsTextureProxy(GrContext* ctx, const GrS // If the caller expects the pixels in a different color space than the one from the image, // apply a color conversion to do this. std::unique_ptr colorConversionProcessor = - GrColorSpaceXformEffect::Make(srcColorSpace, kOpaque_SkAlphaType, - dstColorSpace, kOpaque_SkAlphaType); + GrColorSpaceXformEffect::Make(srcColorSpace, kPremul_SkAlphaType, dstColorSpace); if (colorConversionProcessor) { paint.addColorFragmentProcessor(std::move(colorConversionProcessor)); } diff --git a/src/image/SkImage.cpp b/src/image/SkImage.cpp index 509f607f9d..00b71174f6 100644 --- a/src/image/SkImage.cpp +++ b/src/image/SkImage.cpp @@ -300,7 +300,8 @@ bool SkImage::isAlphaOnly() const { } sk_sp SkImage::makeColorSpace(sk_sp target) const { - if (!target) { + SkColorSpaceTransferFn fn; + if (!target || !target->isNumericalTransferFn(&fn)) { return nullptr; } @@ -312,8 +313,11 @@ sk_sp SkImage::makeColorSpace(sk_sp target) const { return sk_ref_sp(const_cast(this)); } + // TODO: Re-visit this! Keep existing color type? + SkColorType targetColorType = kN32_SkColorType; + // TODO: We might consider making this a deferred conversion? - return as_IB(this)->onMakeColorSpace(std::move(target)); + return as_IB(this)->onMakeColorSpace(std::move(target), targetColorType); } sk_sp SkImage::makeNonTextureImage() const { diff --git a/src/image/SkImage_Base.h b/src/image/SkImage_Base.h index 2682d32e46..3adf51e40a 100644 --- a/src/image/SkImage_Base.h +++ b/src/image/SkImage_Base.h @@ -93,7 +93,7 @@ public: virtual bool onPinAsTexture(GrContext*) const { return false; } virtual void onUnpinAsTexture(GrContext*) const {} - virtual sk_sp onMakeColorSpace(sk_sp) const = 0; + virtual sk_sp onMakeColorSpace(sk_sp, SkColorType) const = 0; protected: SkImage_Base(int width, int height, uint32_t uniqueID); diff --git a/src/image/SkImage_Gpu.cpp b/src/image/SkImage_Gpu.cpp index c2bfeac8ba..5e81474e4f 100644 --- a/src/image/SkImage_Gpu.cpp +++ b/src/image/SkImage_Gpu.cpp @@ -1012,9 +1012,17 @@ bool SkImage::MakeBackendTextureFromSkImage(GrContext* ctx, /////////////////////////////////////////////////////////////////////////////////////////////////// -sk_sp SkImage_Gpu::onMakeColorSpace(sk_sp target) const { - auto xform = GrColorSpaceXformEffect::Make(fColorSpace.get(), this->alphaType(), - target.get(), this->alphaType()); +sk_sp SkImage_Gpu::onMakeColorSpace(sk_sp target, SkColorType) const { + sk_sp srcSpace = fColorSpace; + if (!fColorSpace) { + if (target->isSRGB()) { + return sk_ref_sp(const_cast((SkImage*)this)); + } + + srcSpace = SkColorSpace::MakeSRGB(); + } + + auto xform = GrColorSpaceXformEffect::Make(srcSpace.get(), this->alphaType(), target.get()); if (!xform) { return sk_ref_sp(const_cast(this)); } @@ -1040,10 +1048,13 @@ sk_sp SkImage_Gpu::onMakeColorSpace(sk_sp target) const { return nullptr; } + SkAlphaType newAlphaType = (kUnpremul_SkAlphaType == fAlphaType) ? kPremul_SkAlphaType + : fAlphaType; // MDB: this call is okay bc we know 'renderTargetContext' was exact return sk_make_sp(fContext, kNeedNewImageUniqueID, - fAlphaType, renderTargetContext->asTextureProxyRef(), + newAlphaType, renderTargetContext->asTextureProxyRef(), std::move(target), fBudgeted); + } bool SkImage_Gpu::onIsValid(GrContext* context) const { diff --git a/src/image/SkImage_Gpu.h b/src/image/SkImage_Gpu.h index 1a7f32353b..b7febb5008 100644 --- a/src/image/SkImage_Gpu.h +++ b/src/image/SkImage_Gpu.h @@ -59,7 +59,7 @@ public: sk_sp refColorSpace() { return fColorSpace; } - sk_sp onMakeColorSpace(sk_sp) const override; + sk_sp onMakeColorSpace(sk_sp, SkColorType) const override; typedef ReleaseContext TextureContext; typedef void (*TextureFulfillProc)(TextureContext textureContext, GrBackendTexture* outTexture); diff --git a/src/image/SkImage_Lazy.cpp b/src/image/SkImage_Lazy.cpp index 9a7beadc2f..6aa0ca0549 100644 --- a/src/image/SkImage_Lazy.cpp +++ b/src/image/SkImage_Lazy.cpp @@ -311,7 +311,8 @@ sk_sp SkImage_Lazy::onMakeSubset(const SkIRect& subset) const { return validator ? sk_sp(new SkImage_Lazy(&validator)) : nullptr; } -sk_sp SkImage_Lazy::onMakeColorSpace(sk_sp target) const { +sk_sp SkImage_Lazy::onMakeColorSpace(sk_sp target, + SkColorType targetColorType) const { SkAutoExclusive autoAquire(fOnMakeColorSpaceMutex); if (target && fOnMakeColorSpaceTarget && SkColorSpace::Equals(target.get(), fOnMakeColorSpaceTarget.get())) { diff --git a/src/image/SkImage_Lazy.h b/src/image/SkImage_Lazy.h index 95d78cd904..0e047be9e4 100644 --- a/src/image/SkImage_Lazy.h +++ b/src/image/SkImage_Lazy.h @@ -61,7 +61,7 @@ public: sk_sp onMakeSubset(const SkIRect&) const override; bool getROPixels(SkBitmap*, SkColorSpace* dstColorSpace, CachingHint) const override; bool onIsLazyGenerated() const override { return true; } - sk_sp onMakeColorSpace(sk_sp) const override; + sk_sp onMakeColorSpace(sk_sp, SkColorType) const override; bool onIsValid(GrContext*) const override; diff --git a/src/image/SkImage_Raster.cpp b/src/image/SkImage_Raster.cpp index ac3ddb7a8a..859014f398 100644 --- a/src/image/SkImage_Raster.cpp +++ b/src/image/SkImage_Raster.cpp @@ -110,7 +110,7 @@ public: SkASSERT(bitmapMayBeMutable || fBitmap.isImmutable()); } - sk_sp onMakeColorSpace(sk_sp) const override; + sk_sp onMakeColorSpace(sk_sp, SkColorType) const override; bool onIsValid(GrContext* context) const override { return true; } @@ -341,7 +341,8 @@ bool SkImage_Raster::onAsLegacyBitmap(SkBitmap* bitmap) const { /////////////////////////////////////////////////////////////////////////////// -sk_sp SkImage_Raster::onMakeColorSpace(sk_sp target) const { +sk_sp SkImage_Raster::onMakeColorSpace(sk_sp target, + SkColorType targetColorType) const { SkPixmap src; SkAssertResult(fBitmap.peekPixels(&src)); @@ -354,7 +355,7 @@ sk_sp SkImage_Raster::onMakeColorSpace(sk_sp target) cons src.setColorSpace(SkColorSpace::MakeSRGB()); } - SkImageInfo dstInfo = fBitmap.info().makeColorSpace(target); + SkImageInfo dstInfo = fBitmap.info().makeColorType(targetColorType).makeColorSpace(target); SkBitmap dst; dst.allocPixels(dstInfo);