aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--example/HelloWorld.cpp3
-rw-r--r--gyp/core.gyp1
-rw-r--r--gyp/effects.gyp1
-rw-r--r--include/gpu/GrCaps.h2
-rw-r--r--include/gpu/GrColor.h17
-rw-r--r--include/gpu/GrTextureParams.h31
-rw-r--r--include/gpu/GrTypes.h23
-rw-r--r--include/gpu/SkGr.h7
-rw-r--r--samplecode/SampleApp.cpp3
-rw-r--r--src/core/SkImageCacherator.cpp5
-rw-r--r--src/core/SkSpecialImage.cpp6
-rw-r--r--src/effects/SkTableColorFilter.cpp3
-rw-r--r--src/effects/gradients/SkGradientShader.cpp4
-rw-r--r--src/gpu/GrCaps.cpp18
-rw-r--r--src/gpu/SkGpuDevice.cpp9
-rw-r--r--src/gpu/SkGr.cpp71
-rw-r--r--src/gpu/SkGrPixelRef.cpp2
-rw-r--r--src/gpu/SkGrPriv.h2
-rw-r--r--src/gpu/effects/GrConfigConversionEffect.cpp5
-rw-r--r--src/gpu/effects/GrTextureStripAtlas.cpp2
-rw-r--r--src/gpu/gl/GrGLCaps.cpp43
-rw-r--r--src/gpu/gl/GrGLCaps.h3
-rw-r--r--src/gpu/gl/GrGLDefines.h5
-rw-r--r--src/gpu/gl/GrGLGpu.cpp35
-rw-r--r--src/gpu/gl/GrGLGpu.h3
-rw-r--r--src/gpu/gl/GrGLTexture.h1
-rw-r--r--src/image/SkImage_Gpu.cpp3
-rw-r--r--src/views/SkWindow.cpp8
-rw-r--r--tests/ReadPixelsTest.cpp3
29 files changed, 235 insertions, 84 deletions
diff --git a/example/HelloWorld.cpp b/example/HelloWorld.cpp
index bb29a0c3f5..892dce1c80 100644
--- a/example/HelloWorld.cpp
+++ b/example/HelloWorld.cpp
@@ -157,7 +157,8 @@ void HelloWorldWindow::draw(SkCanvas* canvas) {
fRenderTarget->writePixels(0, 0, snap->width(), snap->height(),
SkImageInfo2GrPixelConfig(info.colorType(),
info.alphaType(),
- info.profileType()),
+ info.profileType(),
+ *fContext->caps()),
pmap.addr(),
pmap.rowBytes(),
GrContext::kFlushWrites_PixelOp);
diff --git a/gyp/core.gyp b/gyp/core.gyp
index 13b8217fb1..68e1436b11 100644
--- a/gyp/core.gyp
+++ b/gyp/core.gyp
@@ -20,6 +20,7 @@
'../include/c',
'../include/config',
'../include/core',
+ '../include/gpu',
'../include/pathops',
'../include/ports',
'../include/private',
diff --git a/gyp/effects.gyp b/gyp/effects.gyp
index 2402ed1c44..8333a53b83 100644
--- a/gyp/effects.gyp
+++ b/gyp/effects.gyp
@@ -21,6 +21,7 @@
'include_dirs': [
'../include/effects',
'../include/client/android',
+ '../include/gpu',
'../include/private',
'../src/effects',
'../src/opts',
diff --git a/include/gpu/GrCaps.h b/include/gpu/GrCaps.h
index 60f213950e..b806dcbabc 100644
--- a/include/gpu/GrCaps.h
+++ b/include/gpu/GrCaps.h
@@ -137,6 +137,7 @@ public:
/** To avoid as-yet-unnecessary complexity we don't allow any partial support of MIP Maps (e.g.
only for POT textures) */
bool mipMapSupport() const { return fMipMapSupport; }
+ bool srgbSupport() const { return fSRGBSupport; }
bool twoSidedStencilSupport() const { return fTwoSidedStencilSupport; }
bool stencilWrapOpsSupport() const { return fStencilWrapOpsSupport; }
bool discardRenderTargetSupport() const { return fDiscardRenderTargetSupport; }
@@ -268,6 +269,7 @@ protected:
bool fNPOTTextureTileSupport : 1;
bool fMipMapSupport : 1;
+ bool fSRGBSupport : 1;
bool fTwoSidedStencilSupport : 1;
bool fStencilWrapOpsSupport : 1;
bool fDiscardRenderTargetSupport : 1;
diff --git a/include/gpu/GrColor.h b/include/gpu/GrColor.h
index 6b83237626..77f1a6cb08 100644
--- a/include/gpu/GrColor.h
+++ b/include/gpu/GrColor.h
@@ -208,7 +208,6 @@ static inline char GrColorComponentFlagToChar(GrColorComponentFlags component) {
}
static inline uint32_t GrPixelConfigComponentMask(GrPixelConfig config) {
- SkASSERT(config >= 0 && config < kGrPixelConfigCnt);
static const uint32_t kFlags[] = {
0, // kUnknown_GrPixelConfig
kA_GrColorComponentFlag, // kAlpha_8_GrPixelConfig
@@ -218,6 +217,7 @@ static inline uint32_t GrPixelConfigComponentMask(GrPixelConfig config) {
kRGBA_GrColorComponentFlags, // kRGBA_8888_GrPixelConfig
kRGBA_GrColorComponentFlags, // kBGRA_8888_GrPixelConfig
kRGBA_GrColorComponentFlags, // kSRGBA_8888_GrPixelConfig
+ kRGBA_GrColorComponentFlags, // kSBGRA_8888_GrPixelConfig
kRGB_GrColorComponentFlags, // kETC1_GrPixelConfig
kA_GrColorComponentFlag, // kLATC_GrPixelConfig
kA_GrColorComponentFlag, // kR11_EAC_GrPixelConfig
@@ -236,13 +236,14 @@ static inline uint32_t GrPixelConfigComponentMask(GrPixelConfig config) {
GR_STATIC_ASSERT(5 == kRGBA_8888_GrPixelConfig);
GR_STATIC_ASSERT(6 == kBGRA_8888_GrPixelConfig);
GR_STATIC_ASSERT(7 == kSRGBA_8888_GrPixelConfig);
- GR_STATIC_ASSERT(8 == kETC1_GrPixelConfig);
- GR_STATIC_ASSERT(9 == kLATC_GrPixelConfig);
- GR_STATIC_ASSERT(10 == kR11_EAC_GrPixelConfig);
- GR_STATIC_ASSERT(11 == kASTC_12x12_GrPixelConfig);
- GR_STATIC_ASSERT(12 == kRGBA_float_GrPixelConfig);
- GR_STATIC_ASSERT(13 == kAlpha_half_GrPixelConfig);
- GR_STATIC_ASSERT(14 == kRGBA_half_GrPixelConfig);
+ GR_STATIC_ASSERT(8 == kSBGRA_8888_GrPixelConfig);
+ GR_STATIC_ASSERT(9 == kETC1_GrPixelConfig);
+ GR_STATIC_ASSERT(10 == kLATC_GrPixelConfig);
+ GR_STATIC_ASSERT(11 == kR11_EAC_GrPixelConfig);
+ GR_STATIC_ASSERT(12 == kASTC_12x12_GrPixelConfig);
+ GR_STATIC_ASSERT(13 == kRGBA_float_GrPixelConfig);
+ GR_STATIC_ASSERT(14 == kAlpha_half_GrPixelConfig);
+ GR_STATIC_ASSERT(15 == kRGBA_half_GrPixelConfig);
GR_STATIC_ASSERT(SK_ARRAY_COUNT(kFlags) == kGrPixelConfigCnt);
}
diff --git a/include/gpu/GrTextureParams.h b/include/gpu/GrTextureParams.h
index 3186b1b027..40d9ac5375 100644
--- a/include/gpu/GrTextureParams.h
+++ b/include/gpu/GrTextureParams.h
@@ -24,6 +24,11 @@ public:
static const GrTextureParams gParams(SkShader::kClamp_TileMode, kBilerp_FilterMode);
return gParams;
}
+ static const GrTextureParams& ClampNoFilterForceAllowSRGB() {
+ static const GrTextureParams gParams(SkShader::kClamp_TileMode, kNone_FilterMode,
+ kForceAllowSRGB_SRGBMode);
+ return gParams;
+ }
GrTextureParams() {
this->reset();
@@ -35,10 +40,19 @@ public:
kMipMap_FilterMode
};
+ enum SRGBMode {
+ kRespectDestination_SRGBMode,
+ kForceAllowSRGB_SRGBMode,
+ };
+
GrTextureParams(SkShader::TileMode tileXAndY, FilterMode filterMode) {
this->reset(tileXAndY, filterMode);
}
+ GrTextureParams(SkShader::TileMode tileXandY, FilterMode filterMode, SRGBMode srgbMode) {
+ this->reset(tileXandY, filterMode, srgbMode);
+ }
+
GrTextureParams(const SkShader::TileMode tileModes[2], FilterMode filterMode) {
this->reset(tileModes, filterMode);
}
@@ -51,6 +65,7 @@ public:
fTileModes[0] = params.fTileModes[0];
fTileModes[1] = params.fTileModes[1];
fFilterMode = params.fFilterMode;
+ fSRGBMode = params.fSRGBMode;
return *this;
}
@@ -61,12 +76,20 @@ public:
void reset(SkShader::TileMode tileXAndY, FilterMode filterMode) {
fTileModes[0] = fTileModes[1] = tileXAndY;
fFilterMode = filterMode;
+ fSRGBMode = kRespectDestination_SRGBMode;
+ }
+
+ void reset(SkShader::TileMode tileXandY, FilterMode filterMode, SRGBMode srgbMode) {
+ fTileModes[0] = fTileModes[1] = tileXandY;
+ fFilterMode = filterMode;
+ fSRGBMode = srgbMode;
}
void reset(const SkShader::TileMode tileModes[2], FilterMode filterMode) {
fTileModes[0] = tileModes[0];
fTileModes[1] = tileModes[1];
fFilterMode = filterMode;
+ fSRGBMode = kRespectDestination_SRGBMode;
}
void setClampNoFilter() {
@@ -84,6 +107,8 @@ public:
void setTileModeY(const SkShader::TileMode tm) { fTileModes[1] = tm; }
void setTileModeXAndY(const SkShader::TileMode tm) { fTileModes[0] = fTileModes[1] = tm; }
+ void setSRGBMode(SRGBMode srgbMode) { fSRGBMode = srgbMode; }
+
SkShader::TileMode getTileModeX() const { return fTileModes[0]; }
SkShader::TileMode getTileModeY() const { return fTileModes[1]; }
@@ -95,10 +120,13 @@ public:
FilterMode filterMode() const { return fFilterMode; }
+ SRGBMode srgbMode() const { return fSRGBMode; }
+
bool operator== (const GrTextureParams& other) const {
return fTileModes[0] == other.fTileModes[0] &&
fTileModes[1] == other.fTileModes[1] &&
- fFilterMode == other.fFilterMode;
+ fFilterMode == other.fFilterMode &&
+ fSRGBMode == other.fSRGBMode;
}
bool operator!= (const GrTextureParams& other) const { return !(*this == other); }
@@ -106,5 +134,6 @@ public:
private:
SkShader::TileMode fTileModes[2];
FilterMode fFilterMode;
+ SRGBMode fSRGBMode;
};
#endif
diff --git a/include/gpu/GrTypes.h b/include/gpu/GrTypes.h
index 3def9aaa99..9be500d3b2 100644
--- a/include/gpu/GrTypes.h
+++ b/include/gpu/GrTypes.h
@@ -218,6 +218,10 @@ enum GrPixelConfig {
*/
kSRGBA_8888_GrPixelConfig,
/**
+ * Premultiplied and sRGB. Byte order is b,g,r,a.
+ */
+ kSBGRA_8888_GrPixelConfig,
+ /**
* ETC1 Compressed Data
*/
kETC1_GrPixelConfig,
@@ -268,8 +272,10 @@ static const int kGrPixelConfigCnt = kLast_GrPixelConfig + 1;
#endif
#if SK_PMCOLOR_BYTE_ORDER(B,G,R,A)
static const GrPixelConfig kSkia8888_GrPixelConfig = kBGRA_8888_GrPixelConfig;
+ static const GrPixelConfig kSkiaGamma8888_GrPixelConfig = kSBGRA_8888_GrPixelConfig;
#elif SK_PMCOLOR_BYTE_ORDER(R,G,B,A)
static const GrPixelConfig kSkia8888_GrPixelConfig = kRGBA_8888_GrPixelConfig;
+ static const GrPixelConfig kSkiaGamma8888_GrPixelConfig = kSRGBA_8888_GrPixelConfig;
#else
#error "SK_*32_SHIFT values must correspond to GL_BGRA or GL_RGBA format."
#endif
@@ -311,6 +317,7 @@ static inline bool GrPixelConfigIs8888(GrPixelConfig config) {
case kRGBA_8888_GrPixelConfig:
case kBGRA_8888_GrPixelConfig:
case kSRGBA_8888_GrPixelConfig:
+ case kSBGRA_8888_GrPixelConfig:
return true;
default:
return false;
@@ -322,6 +329,7 @@ static inline bool GrPixelConfigIs8888(GrPixelConfig config) {
static inline bool GrPixelConfigIsSRGB(GrPixelConfig config) {
switch (config) {
case kSRGBA_8888_GrPixelConfig:
+ case kSBGRA_8888_GrPixelConfig:
return true;
default:
return false;
@@ -336,6 +344,10 @@ static inline GrPixelConfig GrPixelConfigSwapRAndB(GrPixelConfig config) {
return kRGBA_8888_GrPixelConfig;
case kRGBA_8888_GrPixelConfig:
return kBGRA_8888_GrPixelConfig;
+ case kSBGRA_8888_GrPixelConfig:
+ return kSRGBA_8888_GrPixelConfig;
+ case kSRGBA_8888_GrPixelConfig:
+ return kSBGRA_8888_GrPixelConfig;
default:
return kUnknown_GrPixelConfig;
}
@@ -353,6 +365,7 @@ static inline size_t GrBytesPerPixel(GrPixelConfig config) {
case kRGBA_8888_GrPixelConfig:
case kBGRA_8888_GrPixelConfig:
case kSRGBA_8888_GrPixelConfig:
+ case kSBGRA_8888_GrPixelConfig:
return 4;
case kRGBA_half_GrPixelConfig:
return 8;
@@ -386,6 +399,16 @@ static inline bool GrPixelConfigIsAlphaOnly(GrPixelConfig config) {
}
}
+static inline bool GrAllowSRGBForDestinationPixelConfig(GrPixelConfig config) {
+ switch (config) {
+ case kRGBA_8888_GrPixelConfig:
+ case kBGRA_8888_GrPixelConfig:
+ return false;
+ default:
+ return true;
+ }
+}
+
/**
* Optional bitfield flags that can be set on GrSurfaceDesc (below).
*/
diff --git a/include/gpu/SkGr.h b/include/gpu/SkGr.h
index aacc5d25db..6a73636c69 100644
--- a/include/gpu/SkGr.h
+++ b/include/gpu/SkGr.h
@@ -15,6 +15,7 @@
#include "SkFilterQuality.h"
#include "SkImageInfo.h"
+class GrCaps;
class GrContext;
class GrTexture;
class GrTextureParams;
@@ -70,10 +71,10 @@ static inline GrColor SkPMColorToGrColor(SkPMColor c) {
GrTexture* GrRefCachedBitmapTexture(GrContext*, const SkBitmap&, const GrTextureParams&);
// TODO: Move SkImageInfo2GrPixelConfig to SkGrPriv.h (requires cleanup to SkWindow its subclasses).
-GrPixelConfig SkImageInfo2GrPixelConfig(SkColorType, SkAlphaType, SkColorProfileType);
+GrPixelConfig SkImageInfo2GrPixelConfig(SkColorType, SkAlphaType, SkColorProfileType, const GrCaps&);
-static inline GrPixelConfig SkImageInfo2GrPixelConfig(const SkImageInfo& info) {
- return SkImageInfo2GrPixelConfig(info.colorType(), info.alphaType(), info.profileType());
+static inline GrPixelConfig SkImageInfo2GrPixelConfig(const SkImageInfo& info, const GrCaps& caps) {
+ return SkImageInfo2GrPixelConfig(info.colorType(), info.alphaType(), info.profileType(), caps);
}
GrTextureParams::FilterMode GrSkFilterQualityToGrFilterMode(SkFilterQuality paintFilterQuality,
diff --git a/samplecode/SampleApp.cpp b/samplecode/SampleApp.cpp
index 72122234d9..ed1dbc77a2 100644
--- a/samplecode/SampleApp.cpp
+++ b/samplecode/SampleApp.cpp
@@ -310,7 +310,8 @@ public:
fCurRenderTarget->writePixels(0, 0, bm.width(), bm.height(),
SkImageInfo2GrPixelConfig(bm.colorType(),
bm.alphaType(),
- bm.profileType()),
+ bm.profileType(),
+ *fCurContext->caps()),
bm.getPixels(),
bm.rowBytes(),
GrContext::kFlushWrites_PixelOp);
diff --git a/src/core/SkImageCacherator.cpp b/src/core/SkImageCacherator.cpp
index 12c09cbe0a..bb389e986b 100644
--- a/src/core/SkImageCacherator.cpp
+++ b/src/core/SkImageCacherator.cpp
@@ -171,7 +171,8 @@ bool SkImageCacherator::lockAsBitmap(SkBitmap* bitmap, const SkImage* client,
}
const uint32_t pixelOpsFlags = 0;
- if (!tex->readPixels(0, 0, bitmap->width(), bitmap->height(), SkImageInfo2GrPixelConfig(fInfo),
+ if (!tex->readPixels(0, 0, bitmap->width(), bitmap->height(),
+ SkImageInfo2GrPixelConfig(fInfo, *tex->getContext()->caps()),
bitmap->getPixels(), bitmap->rowBytes(), pixelOpsFlags)) {
bitmap->reset();
return false;
@@ -273,7 +274,7 @@ GrTexture* SkImageCacherator::lockTexture(GrContext* ctx, const GrUniqueKey& key
}
}
- const GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(fInfo);
+ const GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(fInfo, *ctx->caps());
// 3. Ask the generator to return a compressed form that the GPU might support
SkAutoTUnref<SkData> data(this->refEncoded(ctx));
diff --git a/src/core/SkSpecialImage.cpp b/src/core/SkSpecialImage.cpp
index b17d5d4147..b59bb41405 100644
--- a/src/core/SkSpecialImage.cpp
+++ b/src/core/SkSpecialImage.cpp
@@ -10,6 +10,8 @@
#include "SkSpecialImage.h"
#include "SkSpecialSurface.h"
+#include "GrContext.h"
+
///////////////////////////////////////////////////////////////////////////////
class SkSpecialImage_Base : public SkSpecialImage {
public:
@@ -166,7 +168,7 @@ public:
#if SK_SUPPORT_GPU
GrTexture* texture = as_IB(fImage.get())->peekTexture();
if (texture) {
- GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info);
+ GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info, *texture->getContext()->caps());
desc.fFlags = kRenderTarget_GrSurfaceFlag;
return SkSpecialSurface::NewRenderTarget(this->proxy(), texture->getContext(), desc);
@@ -384,7 +386,7 @@ public:
}
SkSpecialSurface* onNewSurface(const SkImageInfo& info) const override {
- GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info);
+ GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(info, *fTexture->getContext()->caps());
desc.fFlags = kRenderTarget_GrSurfaceFlag;
return SkSpecialSurface::NewRenderTarget(this->proxy(), fTexture->getContext(), desc);
diff --git a/src/effects/SkTableColorFilter.cpp b/src/effects/SkTableColorFilter.cpp
index 3a6c070fab..f49043f512 100644
--- a/src/effects/SkTableColorFilter.cpp
+++ b/src/effects/SkTableColorFilter.cpp
@@ -7,6 +7,7 @@
#include "SkTableColorFilter.h"
+#include "GrContext.h"
#include "SkBitmap.h"
#include "SkColorPriv.h"
#include "SkReadBuffer.h"
@@ -466,7 +467,7 @@ const GrFragmentProcessor* ColorTableEffect::Create(GrContext* context, SkBitmap
desc.fHeight = 128;
desc.fRowHeight = bitmap.height();
desc.fContext = context;
- desc.fConfig = SkImageInfo2GrPixelConfig(bitmap.info());
+ desc.fConfig = SkImageInfo2GrPixelConfig(bitmap.info(), *context->caps());
GrTextureStripAtlas* atlas = GrTextureStripAtlas::GetAtlas(desc);
int row = atlas->lockRow(bitmap);
SkAutoTUnref<GrTexture> texture;
diff --git a/src/effects/gradients/SkGradientShader.cpp b/src/effects/gradients/SkGradientShader.cpp
index 9fe6c91a01..6a8befd81d 100644
--- a/src/effects/gradients/SkGradientShader.cpp
+++ b/src/effects/gradients/SkGradientShader.cpp
@@ -12,6 +12,8 @@
#include "SkTwoPointConicalGradient.h"
#include "SkSweepGradient.h"
+#include "GrContext.h"
+
void SkGradientShaderBase::Descriptor::flatten(SkWriteBuffer& buffer) const {
buffer.writeColorArray(fColors, fCount);
if (fPos) {
@@ -1117,7 +1119,7 @@ GrGradientEffect::GrGradientEffect(GrContext* ctx,
desc.fHeight = 32;
desc.fRowHeight = bitmap.height();
desc.fContext = ctx;
- desc.fConfig = SkImageInfo2GrPixelConfig(bitmap.info());
+ desc.fConfig = SkImageInfo2GrPixelConfig(bitmap.info(), *ctx->caps());
fAtlas = GrTextureStripAtlas::GetAtlas(desc);
SkASSERT(fAtlas);
diff --git a/src/gpu/GrCaps.cpp b/src/gpu/GrCaps.cpp
index c544d6ef77..000f90c6a6 100644
--- a/src/gpu/GrCaps.cpp
+++ b/src/gpu/GrCaps.cpp
@@ -83,6 +83,7 @@ void GrShaderCaps::applyOptionsOverrides(const GrContextOptions& options) {
GrCaps::GrCaps(const GrContextOptions& options) {
fMipMapSupport = false;
fNPOTTextureTileSupport = false;
+ fSRGBSupport = false;
fTwoSidedStencilSupport = false;
fStencilWrapOpsSupport = false;
fDiscardRenderTargetSupport = false;
@@ -157,6 +158,7 @@ SkString GrCaps::dump() const {
static const char* gNY[] = {"NO", "YES"};
r.appendf("MIP Map Support : %s\n", gNY[fMipMapSupport]);
r.appendf("NPOT Texture Tile Support : %s\n", gNY[fNPOTTextureTileSupport]);
+ r.appendf("sRGB Support : %s\n", gNY[fSRGBSupport]);
r.appendf("Two Sided Stencil Support : %s\n", gNY[fTwoSidedStencilSupport]);
r.appendf("Stencil Wrap Ops Support : %s\n", gNY[fStencilWrapOpsSupport]);
r.appendf("Discard Render Target Support : %s\n", gNY[fDiscardRenderTargetSupport]);
@@ -210,6 +212,7 @@ SkString GrCaps::dump() const {
"RGBA8888", // kRGBA_8888_GrPixelConfig,
"BGRA8888", // kBGRA_8888_GrPixelConfig,
"SRGBA8888",// kSRGBA_8888_GrPixelConfig,
+ "SBGRA8888",// kSBGRA_8888_GrPixelConfig,
"ETC1", // kETC1_GrPixelConfig,
"LATC", // kLATC_GrPixelConfig,
"R11EAC", // kR11_EAC_GrPixelConfig,
@@ -226,13 +229,14 @@ SkString GrCaps::dump() const {
GR_STATIC_ASSERT(5 == kRGBA_8888_GrPixelConfig);
GR_STATIC_ASSERT(6 == kBGRA_8888_GrPixelConfig);
GR_STATIC_ASSERT(7 == kSRGBA_8888_GrPixelConfig);
- GR_STATIC_ASSERT(8 == kETC1_GrPixelConfig);
- GR_STATIC_ASSERT(9 == kLATC_GrPixelConfig);
- GR_STATIC_ASSERT(10 == kR11_EAC_GrPixelConfig);
- GR_STATIC_ASSERT(11 == kASTC_12x12_GrPixelConfig);
- GR_STATIC_ASSERT(12 == kRGBA_float_GrPixelConfig);
- GR_STATIC_ASSERT(13 == kAlpha_half_GrPixelConfig);
- GR_STATIC_ASSERT(14 == kRGBA_half_GrPixelConfig);
+ GR_STATIC_ASSERT(8 == kSBGRA_8888_GrPixelConfig);
+ GR_STATIC_ASSERT(9 == kETC1_GrPixelConfig);
+ GR_STATIC_ASSERT(10 == kLATC_GrPixelConfig);
+ GR_STATIC_ASSERT(11 == kR11_EAC_GrPixelConfig);
+ GR_STATIC_ASSERT(12 == kASTC_12x12_GrPixelConfig);
+ GR_STATIC_ASSERT(13 == kRGBA_float_GrPixelConfig);
+ GR_STATIC_ASSERT(14 == kAlpha_half_GrPixelConfig);
+ GR_STATIC_ASSERT(15 == kRGBA_half_GrPixelConfig);
GR_STATIC_ASSERT(SK_ARRAY_COUNT(kConfigNames) == kGrPixelConfigCnt);
SkASSERT(!this->isConfigRenderable(kUnknown_GrPixelConfig, false));
diff --git a/src/gpu/SkGpuDevice.cpp b/src/gpu/SkGpuDevice.cpp
index c2d8bdad32..823e9b84ff 100644
--- a/src/gpu/SkGpuDevice.cpp
+++ b/src/gpu/SkGpuDevice.cpp
@@ -193,6 +193,7 @@ GrRenderTarget* SkGpuDevice::CreateRenderTarget(
SkColorType ct = origInfo.colorType();
SkAlphaType at = origInfo.alphaType();
+ SkColorProfileType pt = origInfo.profileType();
if (kRGB_565_SkColorType == ct) {
at = kOpaque_SkAlphaType; // force this setting
} else if (ct != kBGRA_8888_SkColorType && ct != kRGBA_8888_SkColorType) {
@@ -202,13 +203,13 @@ GrRenderTarget* SkGpuDevice::CreateRenderTarget(
if (kOpaque_SkAlphaType != at) {
at = kPremul_SkAlphaType; // force this setting
}
- const SkImageInfo info = SkImageInfo::Make(origInfo.width(), origInfo.height(), ct, at);
+ const SkImageInfo info = SkImageInfo::Make(origInfo.width(), origInfo.height(), ct, at, pt);
GrSurfaceDesc desc;
desc.fFlags = kRenderTarget_GrSurfaceFlag;
desc.fWidth = info.width();
desc.fHeight = info.height();
- desc.fConfig = SkImageInfo2GrPixelConfig(info);
+ desc.fConfig = SkImageInfo2GrPixelConfig(info, *context->caps());
desc.fSampleCnt = sampleCount;
desc.fTextureStorageAllocator = textureStorageAllocator;
desc.fIsMipMapped = false;
@@ -227,7 +228,7 @@ bool SkGpuDevice::onReadPixels(const SkImageInfo& dstInfo, void* dstPixels, size
ASSERT_SINGLE_OWNER
// TODO: teach fRenderTarget to take ImageInfo directly to specify the src pixels
- GrPixelConfig config = SkImageInfo2GrPixelConfig(dstInfo);
+ GrPixelConfig config = SkImageInfo2GrPixelConfig(dstInfo, *fContext->caps());
if (kUnknown_GrPixelConfig == config) {
return false;
}
@@ -244,7 +245,7 @@ bool SkGpuDevice::onWritePixels(const SkImageInfo& info, const void* pixels, siz
int x, int y) {
ASSERT_SINGLE_OWNER
// TODO: teach fRenderTarget to take ImageInfo directly to specify the src pixels
- GrPixelConfig config = SkImageInfo2GrPixelConfig(info);
+ GrPixelConfig config = SkImageInfo2GrPixelConfig(info, *fContext->caps());
if (kUnknown_GrPixelConfig == config) {
return false;
}
diff --git a/src/gpu/SkGr.cpp b/src/gpu/SkGr.cpp
index 1463336c49..866f34d06c 100644
--- a/src/gpu/SkGr.cpp
+++ b/src/gpu/SkGr.cpp
@@ -43,12 +43,12 @@
# include "etc1.h"
#endif
-GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo& info) {
+GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo& info, const GrCaps& caps) {
GrSurfaceDesc desc;
desc.fFlags = kNone_GrSurfaceFlags;
desc.fWidth = info.width();
desc.fHeight = info.height();
- desc.fConfig = SkImageInfo2GrPixelConfig(info);
+ desc.fConfig = SkImageInfo2GrPixelConfig(info, caps);
desc.fSampleCnt = 0;
return desc;
}
@@ -213,7 +213,7 @@ static GrTexture* load_etc1_texture(GrContext* ctx, const SkBitmap &bm, GrSurfac
}
GrTexture* GrUploadBitmapToTexture(GrContext* ctx, const SkBitmap& bitmap) {
- GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(bitmap.info());
+ GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(bitmap.info(), *ctx->caps());
if (GrTexture *texture = load_etc1_texture(ctx, bitmap, desc)) {
return texture;
}
@@ -238,8 +238,8 @@ GrTexture* GrUploadPixmapToTexture(GrContext* ctx, const SkPixmap& pixmap) {
SkPixmap tmpPixmap;
SkBitmap tmpBitmap;
- GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(pixmap.info());
const GrCaps* caps = ctx->caps();
+ GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(pixmap.info(), *caps);
if (kIndex_8_SkColorType == pixmap.colorType()) {
if (caps->isConfigTexturable(kIndex_8_GrPixelConfig)) {
@@ -263,7 +263,7 @@ GrTexture* GrUploadPixmapToTexture(GrContext* ctx, const SkPixmap& pixmap) {
}
pmap = &tmpPixmap;
// must rebuild desc, since we've forced the info to be N32
- desc = GrImageInfoToSurfaceDesc(pmap->info());
+ desc = GrImageInfoToSurfaceDesc(pmap->info(), *caps);
}
}
@@ -289,7 +289,7 @@ void GrInstallBitmapUniqueKeyInvalidator(const GrUniqueKey& key, SkPixelRef* pix
GrTexture* GrGenerateMipMapsAndUploadToTexture(GrContext* ctx, const SkBitmap& bitmap)
{
- GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(bitmap.info());
+ GrSurfaceDesc desc = GrImageInfoToSurfaceDesc(bitmap.info(), *ctx->caps());
if (kIndex_8_SkColorType != bitmap.colorType() && !bitmap.readyToDraw()) {
GrTexture* texture = load_etc1_texture(ctx, bitmap, desc);
if (texture) {
@@ -358,29 +358,38 @@ GrTexture* GrRefCachedBitmapTexture(GrContext* ctx, const SkBitmap& bitmap,
// alphatype is ignore for now, but if GrPixelConfig is expanded to encompass
// alpha info, that will be considered.
-GrPixelConfig SkImageInfo2GrPixelConfig(SkColorType ct, SkAlphaType, SkColorProfileType pt) {
- switch (ct) {
- case kUnknown_SkColorType:
- return kUnknown_GrPixelConfig;
- case kAlpha_8_SkColorType:
- return kAlpha_8_GrPixelConfig;
- case kRGB_565_SkColorType:
- return kRGB_565_GrPixelConfig;
- case kARGB_4444_SkColorType:
- return kRGBA_4444_GrPixelConfig;
- case kRGBA_8888_SkColorType:
- //if (kSRGB_SkColorProfileType == pt) {
- // return kSRGBA_8888_GrPixelConfig;
- //}
- return kRGBA_8888_GrPixelConfig;
- case kBGRA_8888_SkColorType:
- return kBGRA_8888_GrPixelConfig;
- case kIndex_8_SkColorType:
- return kIndex_8_GrPixelConfig;
- case kGray_8_SkColorType:
- return kAlpha_8_GrPixelConfig; // TODO: gray8 support on gpu
- case kRGBA_F16_SkColorType:
- return kRGBA_half_GrPixelConfig;
+GrPixelConfig SkImageInfo2GrPixelConfig(SkColorType ct, SkAlphaType, SkColorProfileType pt,
+ const GrCaps& caps) {
+ if (kSRGB_SkColorProfileType == pt && caps.srgbSupport()) {
+ switch (ct) {
+ case kRGBA_8888_SkColorType:
+ return kSRGBA_8888_GrPixelConfig;
+ case kBGRA_8888_SkColorType:
+ return kSBGRA_8888_GrPixelConfig;
+ default:
+ break;
+ }
+ } else {
+ switch (ct) {
+ case kUnknown_SkColorType:
+ return kUnknown_GrPixelConfig;
+ case kAlpha_8_SkColorType:
+ return kAlpha_8_GrPixelConfig;
+ case kRGB_565_SkColorType:
+ return kRGB_565_GrPixelConfig;
+ case kARGB_4444_SkColorType:
+ return kRGBA_4444_GrPixelConfig;
+ case kRGBA_8888_SkColorType:
+ return kRGBA_8888_GrPixelConfig;
+ case kBGRA_8888_SkColorType:
+ return kBGRA_8888_GrPixelConfig;
+ case kIndex_8_SkColorType:
+ return kIndex_8_GrPixelConfig;
+ case kGray_8_SkColorType:
+ return kAlpha_8_GrPixelConfig; // TODO: gray8 support on gpu
+ case kRGBA_F16_SkColorType:
+ return kRGBA_half_GrPixelConfig;
+ }
}
SkASSERT(0); // shouldn't get here
return kUnknown_GrPixelConfig;
@@ -413,6 +422,10 @@ bool GrPixelConfig2ColorAndProfileType(GrPixelConfig config, SkColorType* ctOut,
ct = kRGBA_8888_SkColorType;
pt = kSRGB_SkColorProfileType;
break;
+ case kSBGRA_8888_GrPixelConfig:
+ ct = kBGRA_8888_SkColorType;
+ pt = kSRGB_SkColorProfileType;
+ break;
default:
return false;
}
diff --git a/src/gpu/SkGrPixelRef.cpp b/src/gpu/SkGrPixelRef.cpp
index f61d92e186..e21d3b9d6d 100644
--- a/src/gpu/SkGrPixelRef.cpp
+++ b/src/gpu/SkGrPixelRef.cpp
@@ -75,7 +75,7 @@ static SkGrPixelRef* copy_to_new_texture_pixelref(GrTexture* texture, SkColorTyp
srcRect = *subset;
}
desc.fFlags = kRenderTarget_GrSurfaceFlag;
- desc.fConfig = SkImageInfo2GrPixelConfig(dstCT, kPremul_SkAlphaType, dstPT);
+ desc.fConfig = SkImageInfo2GrPixelConfig(dstCT, kPremul_SkAlphaType, dstPT, *context->caps());
desc.fTextureStorageAllocator = texture->desc().fTextureStorageAllocator;
desc.fIsMipMapped = false;
diff --git a/src/gpu/SkGrPriv.h b/src/gpu/SkGrPriv.h
index 555f415513..579216a2ea 100644
--- a/src/gpu/SkGrPriv.h
+++ b/src/gpu/SkGrPriv.h
@@ -95,7 +95,7 @@ bool SkPaintToGrPaintWithTexture(GrContext* context,
//////////////////////////////////////////////////////////////////////////////
-GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo&);
+GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo&, const GrCaps&);
bool GrPixelConfig2ColorAndProfileType(GrPixelConfig, SkColorType*, SkColorProfileType*);
diff --git a/src/gpu/effects/GrConfigConversionEffect.cpp b/src/gpu/effects/GrConfigConversionEffect.cpp
index dc41203406..bedcc78370 100644
--- a/src/gpu/effects/GrConfigConversionEffect.cpp
+++ b/src/gpu/effects/GrConfigConversionEffect.cpp
@@ -98,7 +98,7 @@ GrConfigConversionEffect::GrConfigConversionEffect(GrTexture* texture,
const GrSwizzle& swizzle,
PMConversion pmConversion,
const SkMatrix& matrix)
- : INHERITED(texture, matrix)
+ : INHERITED(texture, matrix, GrTextureParams::ClampNoFilterForceAllowSRGB())
, fSwizzle(swizzle)
, fPMConversion(pmConversion) {
this->initClassID<GrConfigConversionEffect>();
@@ -296,7 +296,8 @@ const GrFragmentProcessor* GrConfigConversionEffect::Create(GrTexture* texture,
// If we returned a GrConfigConversionEffect that was equivalent to a GrSimpleTextureEffect
// then we may pollute our texture cache with redundant shaders. So in the case that no
// conversions were requested we instead return a GrSimpleTextureEffect.
- return GrSimpleTextureEffect::Create(texture, matrix);
+ return GrSimpleTextureEffect::Create(texture, matrix,
+ GrTextureParams::ClampNoFilterForceAllowSRGB());
} else {
if (kRGBA_8888_GrPixelConfig != texture->config() &&
kBGRA_8888_GrPixelConfig != texture->config() &&
diff --git a/src/gpu/effects/GrTextureStripAtlas.cpp b/src/gpu/effects/GrTextureStripAtlas.cpp
index 1ac3dab2aa..1543a2e9db 100644
--- a/src/gpu/effects/GrTextureStripAtlas.cpp
+++ b/src/gpu/effects/GrTextureStripAtlas.cpp
@@ -158,7 +158,7 @@ int GrTextureStripAtlas::lockRow(const SkBitmap& data) {
// that is not currently in use
fTexture->writePixels(0, rowNumber * fDesc.fRowHeight,
fDesc.fWidth, fDesc.fRowHeight,
- SkImageInfo2GrPixelConfig(data.info()),
+ SkImageInfo2GrPixelConfig(data.info(), *this->getContext()->caps()),
data.getPixels(),
data.rowBytes(),
GrContext::kDontFlush_PixelOpsFlag);
diff --git a/src/gpu/gl/GrGLCaps.cpp b/src/gpu/gl/GrGLCaps.cpp
index 40885359fb..af31480ba7 100644
--- a/src/gpu/gl/GrGLCaps.cpp
+++ b/src/gpu/gl/GrGLCaps.cpp
@@ -1435,27 +1435,31 @@ void GrGLCaps::initConfigTable(const GrGLContextInfo& ctxInfo, const GrGLInterfa
}
fConfigTable[kBGRA_8888_GrPixelConfig].fSwizzle = GrSwizzle::RGBA();
- // We only enable srgb support if both textures and FBOs support srgb.
- bool srgbSupport = false;
+ // We only enable srgb support if both textures and FBOs support srgb,
+ // *and* we can disable sRGB decode-on-read, to support "legacy" mode.
if (kGL_GrGLStandard == standard) {
if (ctxInfo.version() >= GR_GL_VER(3,0)) {
- srgbSupport = true;
+ fSRGBSupport = true;
} else if (ctxInfo.hasExtension("GL_EXT_texture_sRGB")) {
if (ctxInfo.hasExtension("GL_ARB_framebuffer_sRGB") ||
ctxInfo.hasExtension("GL_EXT_framebuffer_sRGB")) {
- srgbSupport = true;
+ fSRGBSupport = true;
}
}
// All the above srgb extensions support toggling srgb writes
- fSRGBWriteControl = srgbSupport;
+ fSRGBWriteControl = fSRGBSupport;
} else {
// See https://bug.skia.org/4148 for PowerVR issue.
- srgbSupport = kPowerVRRogue_GrGLRenderer != ctxInfo.renderer() &&
+ fSRGBSupport = kPowerVRRogue_GrGLRenderer != ctxInfo.renderer() &&
(ctxInfo.version() >= GR_GL_VER(3,0) || ctxInfo.hasExtension("GL_EXT_sRGB"));
// ES through 3.1 requires EXT_srgb_write_control to support toggling
// sRGB writing for destinations.
fSRGBWriteControl = ctxInfo.hasExtension("GL_EXT_sRGB_write_control");
}
+ if (!ctxInfo.hasExtension("GL_EXT_texture_sRGB_decode")) {
+ // To support "legacy" L32 mode, we require the ability to turn off sRGB decode:
+ fSRGBSupport = false;
+ }
fConfigTable[kSRGBA_8888_GrPixelConfig].fFormats.fBaseInternalFormat = GR_GL_SRGB_ALPHA;
fConfigTable[kSRGBA_8888_GrPixelConfig].fFormats.fSizedInternalFormat = GR_GL_SRGB8_ALPHA8;
// GL does not do srgb<->rgb conversions when transferring between cpu and gpu. Thus, the
@@ -1464,7 +1468,7 @@ void GrGLCaps::initConfigTable(const GrGLContextInfo& ctxInfo, const GrGLInterfa
GR_GL_RGBA;
fConfigTable[kSRGBA_8888_GrPixelConfig].fFormats.fExternalType = GR_GL_UNSIGNED_BYTE;
fConfigTable[kSRGBA_8888_GrPixelConfig].fFormatType = kNormalizedFixedPoint_FormatType;
- if (srgbSupport) {
+ if (fSRGBSupport) {
fConfigTable[kSRGBA_8888_GrPixelConfig].fFlags = ConfigInfo::kTextureable_Flag |
allRenderFlags;
}
@@ -1473,6 +1477,26 @@ void GrGLCaps::initConfigTable(const GrGLContextInfo& ctxInfo, const GrGLInterfa
}
fConfigTable[kSRGBA_8888_GrPixelConfig].fSwizzle = GrSwizzle::RGBA();
+ // sBGRA is not a "real" thing in OpenGL, but GPUs support it, and on platforms where
+ // kN32 == BGRA, we need some way to work with it. (The default framebuffer on Windows
+ // is in this format, for example).
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFormats.fBaseInternalFormat = GR_GL_SRGB_ALPHA;
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFormats.fSizedInternalFormat = GR_GL_SRGB8_ALPHA8;
+ // GL does not do srgb<->rgb conversions when transferring between cpu and gpu. Thus, the
+ // external format is GL_BGRA.
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFormats.fExternalFormat[kOther_ExternalFormatUsage] =
+ GR_GL_BGRA;
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFormats.fExternalType = GR_GL_UNSIGNED_BYTE;
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFormatType = kNormalizedFixedPoint_FormatType;
+ if (fSRGBSupport) {
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFlags = ConfigInfo::kTextureable_Flag |
+ allRenderFlags;
+ }
+ if (texStorageSupported) {
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFlags |= ConfigInfo::kCanUseTexStorage_Flag;
+ }
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fSwizzle = GrSwizzle::RGBA();
+
fConfigTable[kRGB_565_GrPixelConfig].fFormats.fBaseInternalFormat = GR_GL_RGB;
if (this->ES2CompatibilitySupport()) {
fConfigTable[kRGB_565_GrPixelConfig].fFormats.fSizedInternalFormat = GR_GL_RGB565;
@@ -1792,6 +1816,11 @@ void GrGLCaps::initConfigTable(const GrGLContextInfo& ctxInfo, const GrGLInterfa
if (ctxInfo.standard() == kGLES_GrGLStandard && ctxInfo.version() == GR_GL_VER(2,0)) {
fConfigTable[kSRGBA_8888_GrPixelConfig].fFormats.fExternalFormat[kTexImage_ExternalFormatUsage] =
GR_GL_SRGB_ALPHA;
+
+ // Additionally, because we had to "invent" sBGRA, there is no way to make it work
+ // in ES 2.0, because there is no <internalFormat> we can use. So just make that format
+ // unsupported. (If we have no sRGB support at all, this will get overwritten below).
+ fConfigTable[kSBGRA_8888_GrPixelConfig].fFlags = 0;
}
// If BGRA is supported as an internal format it must always be specified to glTex[Sub]Image
diff --git a/src/gpu/gl/GrGLCaps.h b/src/gpu/gl/GrGLCaps.h
index 376610d8b0..ed673e7ce7 100644
--- a/src/gpu/gl/GrGLCaps.h
+++ b/src/gpu/gl/GrGLCaps.h
@@ -120,12 +120,10 @@ public:
const GrGLInterface* glInterface);
bool isConfigTexturable(GrPixelConfig config) const override {
- SkASSERT(kGrPixelConfigCnt > config);
return SkToBool(fConfigTable[config].fFlags & ConfigInfo::kTextureable_Flag);
}
bool isConfigRenderable(GrPixelConfig config, bool withMSAA) const override {
- SkASSERT(kGrPixelConfigCnt > config);
if (withMSAA) {
return SkToBool(fConfigTable[config].fFlags & ConfigInfo::kRenderableWithMSAA_Flag);
} else {
@@ -134,7 +132,6 @@ public:
}
bool isConfigTexSupportEnabled(GrPixelConfig config) const {
- SkASSERT(kGrPixelConfigCnt > config);
return SkToBool(fConfigTable[config].fFlags & ConfigInfo::kCanUseTexStorage_Flag);
}
diff --git a/src/gpu/gl/GrGLDefines.h b/src/gpu/gl/GrGLDefines.h
index cd73be401b..ff4c457250 100644
--- a/src/gpu/gl/GrGLDefines.h
+++ b/src/gpu/gl/GrGLDefines.h
@@ -506,12 +506,17 @@
/* TextureUsage */
#define GR_GL_FRAMEBUFFER_ATTACHMENT 0x93A3
+/* TextureSRGBDecode */
+#define GR_GL_DECODE_EXT 0x8A49
+#define GR_GL_SKIP_DECODE_EXT 0x8A4A
+
/* TextureParameterName */
#define GR_GL_TEXTURE_MAG_FILTER 0x2800
#define GR_GL_TEXTURE_MIN_FILTER 0x2801
#define GR_GL_TEXTURE_WRAP_S 0x2802
#define GR_GL_TEXTURE_WRAP_T 0x2803
#define GR_GL_TEXTURE_USAGE 0x93A2
+#define GR_GL_TEXTURE_SRGB_DECODE_EXT 0x8A48
/* TextureTarget */
/* GL_TEXTURE_2D */
diff --git a/src/gpu/gl/GrGLGpu.cpp b/src/gpu/gl/GrGLGpu.cpp
index 76cb1a068a..62baf79002 100644
--- a/src/gpu/gl/GrGLGpu.cpp
+++ b/src/gpu/gl/GrGLGpu.cpp
@@ -898,6 +898,7 @@ static inline GrGLint config_alignment(GrPixelConfig config) {
case kRGBA_8888_GrPixelConfig:
case kBGRA_8888_GrPixelConfig:
case kSRGBA_8888_GrPixelConfig:
+ case kSBGRA_8888_GrPixelConfig:
case kRGBA_float_GrPixelConfig:
return 4;
default:
@@ -2100,13 +2101,15 @@ bool GrGLGpu::flushGLState(const GrPipeline& pipeline, const GrPrimitiveProcesso
SkSTArray<8, const GrTextureAccess*> textureAccesses;
program->setData(primProc, pipeline, &textureAccesses);
+ GrGLRenderTarget* glRT = static_cast<GrGLRenderTarget*>(pipeline.getRenderTarget());
+ bool allowSRGB = GrAllowSRGBForDestinationPixelConfig(glRT->config());
+
int numTextureAccesses = textureAccesses.count();
for (int i = 0; i < numTextureAccesses; i++) {
- this->bindTexture(i, textureAccesses[i]->getParams(),
+ this->bindTexture(i, textureAccesses[i]->getParams(), allowSRGB,
static_cast<GrGLTexture*>(textureAccesses[i]->getTexture()));
}
- GrGLRenderTarget* glRT = static_cast<GrGLRenderTarget*>(pipeline.getRenderTarget());
this->flushStencil(pipeline.getStencil());
this->flushScissor(pipeline.getScissorState(), glRT->getViewport(), glRT->origin());
this->flushHWAAState(glRT, pipeline.isHWAntialiasState(), !pipeline.getStencil().isDisabled());
@@ -2607,6 +2610,16 @@ bool GrGLGpu::onGetReadPixelsInfo(GrSurface* srcSurface, int width, int height,
tempDrawInfo->fSwizzle = GrSwizzle::BGRA();
tempDrawInfo->fReadConfig = kRGBA_8888_GrPixelConfig;
ElevateDrawPreference(drawPreference, kRequireDraw_DrawPreference);
+ } else if (readConfig == kSBGRA_8888_GrPixelConfig &&
+ this->glCaps().isConfigRenderable(kSRGBA_8888_GrPixelConfig, false) &&
+ this->readPixelsSupported(kSRGBA_8888_GrPixelConfig, kSRGBA_8888_GrPixelConfig)) {
+ // We're trying to read sBGRA but it's not supported. If sRGBA is renderable and
+ // we can read it back, then do a swizzling draw to a sRGBA and read it back (which
+ // will effectively be sBGRA).
+ tempDrawInfo->fTempSurfaceDesc.fConfig = kSRGBA_8888_GrPixelConfig;
+ tempDrawInfo->fSwizzle = GrSwizzle::BGRA();
+ tempDrawInfo->fReadConfig = kSRGBA_8888_GrPixelConfig;
+ ElevateDrawPreference(drawPreference, kRequireDraw_DrawPreference);
} else if (readConfig == kAlpha_8_GrPixelConfig) {
// onReadPixels implements a fallback for cases where we are want to read kAlpha_8,
// it's unsupported, but 32bit RGBA reads are supported.
@@ -3311,7 +3324,8 @@ static void get_tex_param_swizzle(GrPixelConfig config,
}
}
-void GrGLGpu::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTexture* texture) {
+void GrGLGpu::bindTexture(int unitIdx, const GrTextureParams& params, bool dstConfigAllowsSRGB,
+ GrGLTexture* texture) {
SkASSERT(texture);
#ifdef SK_DEBUG
@@ -3347,6 +3361,19 @@ void GrGLGpu::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTextur
bool setAll = timestamp < this->getResetTimestamp();
GrGLTexture::TexParams newTexParams;
+ if (this->caps()->srgbSupport()) {
+ // By default, the decision to allow SRGB decode is based on the destination config.
+ // A texture can override that by specifying a value in GrTextureParams.
+ newTexParams.fSRGBDecode =
+ (dstConfigAllowsSRGB || GrTextureParams::kForceAllowSRGB_SRGBMode == params.srgbMode())
+ ? GR_GL_DECODE_EXT : GR_GL_SKIP_DECODE_EXT;
+
+ if (setAll || newTexParams.fSRGBDecode != oldTexParams.fSRGBDecode) {
+ this->setTextureUnit(unitIdx);
+ GL_CALL(TexParameteri(target, GR_GL_TEXTURE_SRGB_DECODE_EXT, newTexParams.fSRGBDecode));
+ }
+ }
+
static GrGLenum glMinFilterModes[] = {
GR_GL_NEAREST,
GR_GL_LINEAR,
@@ -4014,7 +4041,7 @@ void GrGLGpu::copySurfaceAsDraw(GrSurface* dst,
GrGLTexture* srcTex = static_cast<GrGLTexture*>(src->asTexture());
GrTextureParams params(SkShader::kClamp_TileMode, GrTextureParams::kNone_FilterMode);
- this->bindTexture(0, params, srcTex);
+ this->bindTexture(0, params, true, srcTex);
GrGLIRect dstVP;
this->bindSurfaceFBOForCopy(dst, GR_GL_FRAMEBUFFER, &dstVP, kDst_TempFBOTarget);
diff --git a/src/gpu/gl/GrGLGpu.h b/src/gpu/gl/GrGLGpu.h
index e365601e1f..a3582739e7 100644
--- a/src/gpu/gl/GrGLGpu.h
+++ b/src/gpu/gl/GrGLGpu.h
@@ -59,7 +59,8 @@ public:
void discard(GrRenderTarget*) override;
// Used by GrGLProgram to configure OpenGL state.
- void bindTexture(int unitIdx, const GrTextureParams& params, GrGLTexture* texture);
+ void bindTexture(int unitIdx, const GrTextureParams& params, bool dstConfigAllowsSRGB,
+ GrGLTexture* texture);
bool onGetReadPixelsInfo(GrSurface* srcSurface, int readWidth, int readHeight, size_t rowBytes,
GrPixelConfig readConfig, DrawPreference*,
diff --git a/src/gpu/gl/GrGLTexture.h b/src/gpu/gl/GrGLTexture.h
index 937b8be13e..6ee8dcfe2b 100644
--- a/src/gpu/gl/GrGLTexture.h
+++ b/src/gpu/gl/GrGLTexture.h
@@ -25,6 +25,7 @@ public:
GrGLenum fWrapT;
GrGLenum fMaxMipMapLevel;
GrGLenum fSwizzleRGBA[4];
+ GrGLenum fSRGBDecode;
void invalidate() { memset(this, 0xff, sizeof(TexParams)); }
};
diff --git a/src/image/SkImage_Gpu.cpp b/src/image/SkImage_Gpu.cpp
index 5e687b751a..a1f032f6a1 100644
--- a/src/image/SkImage_Gpu.cpp
+++ b/src/image/SkImage_Gpu.cpp
@@ -111,7 +111,8 @@ static void apply_premul(const SkImageInfo& info, void* pixels, size_t rowBytes)
bool SkImage_Gpu::onReadPixels(const SkImageInfo& info, void* pixels, size_t rowBytes,
int srcX, int srcY, CachingHint) const {
GrPixelConfig config = SkImageInfo2GrPixelConfig(info.colorType(), info.alphaType(),
- info.profileType());
+ info.profileType(),
+ *fTexture->getContext()->caps());
uint32_t flags = 0;
if (kUnpremul_SkAlphaType == info.alphaType() && kPremul_SkAlphaType == fAlphaType) {
// let the GPU perform this transformation for us
diff --git a/src/views/SkWindow.cpp b/src/views/SkWindow.cpp
index 82c1a43c0a..056b3eab50 100644
--- a/src/views/SkWindow.cpp
+++ b/src/views/SkWindow.cpp
@@ -329,9 +329,13 @@ GrRenderTarget* SkWindow::renderTarget(const AttachmentInfo& attachmentInfo,
// TODO: Query the actual framebuffer for sRGB capable. However, to
// preserve old (fake-linear) behavior, we don't do this. Instead, rely
// on the flag (currently driven via 'C' mode in SampleApp).
- desc.fConfig = (info().profileType() == kSRGB_SkColorProfileType ||
+ //
+ // Also, we may not have real sRGB support (ANGLE, in particular), so check for
+ // that, and fall back to L32:
+ desc.fConfig = grContext->caps()->srgbSupport() &&
+ (info().profileType() == kSRGB_SkColorProfileType ||
info().colorType() == kRGBA_F16_SkColorType)
- ? kSRGBA_8888_GrPixelConfig // This may not be the right byte-order
+ ? kSkiaGamma8888_GrPixelConfig
: kSkia8888_GrPixelConfig;
desc.fOrigin = kBottomLeft_GrSurfaceOrigin;
desc.fSampleCnt = attachmentInfo.fSampleCount;
diff --git a/tests/ReadPixelsTest.cpp b/tests/ReadPixelsTest.cpp
index 77a11e5f8b..87e51163da 100644
--- a/tests/ReadPixelsTest.cpp
+++ b/tests/ReadPixelsTest.cpp
@@ -424,7 +424,8 @@ static void test_readpixels_texture(skiatest::Reporter* reporter, GrTexture* tex
GrPixelConfig dstConfig =
SkImageInfo2GrPixelConfig(gReadPixelsConfigs[c].fColorType,
gReadPixelsConfigs[c].fAlphaType,
- kLinear_SkColorProfileType);
+ kLinear_SkColorProfileType,
+ *texture->getContext()->caps());
uint32_t flags = 0;
if (gReadPixelsConfigs[c].fAlphaType == kUnpremul_SkAlphaType) {
flags = GrContext::kUnpremul_PixelOpsFlag;