aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorGravatar msarett <msarett@google.com>2016-04-22 16:27:24 -0700
committerGravatar Commit bot <commit-bot@chromium.org>2016-04-22 16:27:24 -0700
commit34e0ec40b10320765d4a4432f56e090556f9c75e (patch)
treef7b05f9dce7e83b666fe0309519daeab4b8f3f1f
parenta45a668fa57eb968e24f379eceb2e56324e2cca2 (diff)
Support the non-native (RGBA/BGRA) swizzle
-rw-r--r--dm/DM.cpp7
-rw-r--r--dm/DMSrcSink.cpp47
-rw-r--r--dm/DMSrcSink.h1
-rw-r--r--src/codec/SkBmpRLECodec.cpp22
-rw-r--r--src/codec/SkBmpRLECodec.h2
-rw-r--r--src/codec/SkBmpStandardCodec.cpp16
-rw-r--r--src/codec/SkBmpStandardCodec.h2
-rw-r--r--src/codec/SkCodecPriv.h54
-rw-r--r--src/codec/SkGifCodec.cpp3
-rw-r--r--src/codec/SkJpegCodec.cpp17
-rw-r--r--src/codec/SkMaskSwizzler.cpp267
-rw-r--r--src/codec/SkPngCodec.cpp28
-rw-r--r--src/codec/SkPngCodec.h2
-rw-r--r--src/codec/SkSampler.cpp3
-rw-r--r--src/codec/SkSwizzler.cpp284
-rw-r--r--src/codec/SkWbmpCodec.cpp3
16 files changed, 560 insertions, 198 deletions
diff --git a/dm/DM.cpp b/dm/DM.cpp
index 58cb773e03..e77c99c304 100644
--- a/dm/DM.cpp
+++ b/dm/DM.cpp
@@ -365,6 +365,9 @@ static void push_codec_src(Path path, CodecSrc::Mode mode, CodecSrc::DstColorTyp
case CodecSrc::kIndex8_Always_DstColorType:
folder.append("_kIndex8");
break;
+ case CodecSrc::kNonNative8888_Always_DstColorType:
+ folder.append("_kNonNative");
+ break;
default:
break;
}
@@ -410,6 +413,9 @@ static void push_android_codec_src(Path path, AndroidCodecSrc::Mode mode,
case CodecSrc::kIndex8_Always_DstColorType:
folder.append("_kIndex8");
break;
+ case CodecSrc::kNonNative8888_Always_DstColorType:
+ folder.append("_kNonNative");
+ break;
default:
break;
}
@@ -508,6 +514,7 @@ static void push_codec_srcs(Path path) {
SkTArray<CodecSrc::DstColorType> colorTypes;
colorTypes.push_back(CodecSrc::kGetFromCanvas_DstColorType);
+ colorTypes.push_back(CodecSrc::kNonNative8888_Always_DstColorType);
switch (codec->getInfo().colorType()) {
case kGray_8_SkColorType:
colorTypes.push_back(CodecSrc::kGrayscale_Always_DstColorType);
diff --git a/dm/DMSrcSink.cpp b/dm/DMSrcSink.cpp
index c99f326081..dcbd220275 100644
--- a/dm/DMSrcSink.cpp
+++ b/dm/DMSrcSink.cpp
@@ -110,6 +110,9 @@ Error BRDSrc::draw(SkCanvas* canvas) const {
case CodecSrc::kGrayscale_Always_DstColorType:
colorType = kGray_8_SkColorType;
break;
+ default:
+ SkASSERT(false);
+ break;
}
SkAutoTDelete<SkBitmapRegionDecoder> brd(create_brd(fPath, fStrategy));
@@ -271,6 +274,18 @@ bool CodecSrc::veto(SinkFlags flags) const {
return flags.type != SinkFlags::kRaster || flags.approach != SinkFlags::kDirect;
}
+// Allows us to test decodes to non-native 8888.
+void swap_rb_if_necessary(SkBitmap& bitmap, CodecSrc::DstColorType dstColorType) {
+ if (CodecSrc::kNonNative8888_Always_DstColorType != dstColorType) {
+ return;
+ }
+
+ for (int y = 0; y < bitmap.height(); y++) {
+ uint32_t* row = (uint32_t*) bitmap.getAddr(0, y);
+ SkOpts::RGBA_to_BGRA(row, row, bitmap.width());
+ }
+}
+
// FIXME: Currently we cannot draw unpremultiplied sources. skbug.com/3338 and skbug.com/3339.
// This allows us to still test unpremultiplied decodes.
void premultiply_if_necessary(SkBitmap& bitmap) {
@@ -317,6 +332,16 @@ bool get_decode_info(SkImageInfo* decodeInfo, SkColorType canvasColorType,
}
*decodeInfo = decodeInfo->makeColorType(kGray_8_SkColorType);
break;
+ case CodecSrc::kNonNative8888_Always_DstColorType:
+ if (kRGB_565_SkColorType == canvasColorType) {
+ return false;
+ }
+#ifdef SK_PMCOLOR_IS_RGBA
+ *decodeInfo = decodeInfo->makeColorType(kBGRA_8888_SkColorType);
+#else
+ *decodeInfo = decodeInfo->makeColorType(kRGBA_8888_SkColorType);
+#endif
+ break;
default:
if (kRGB_565_SkColorType == canvasColorType &&
kOpaque_SkAlphaType != decodeInfo->alphaType()) {
@@ -378,7 +403,13 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
factory = &zeroFactory;
options.fZeroInitialized = SkCodec::kYes_ZeroInitialized;
}
- if (!bitmap.tryAllocPixels(decodeInfo, factory, colorTable.get())) {
+
+ SkImageInfo bitmapInfo = decodeInfo;
+ if (kRGBA_8888_SkColorType == decodeInfo.colorType() ||
+ kBGRA_8888_SkColorType == decodeInfo.colorType()) {
+ bitmapInfo = bitmapInfo.makeColorType(kN32_SkColorType);
+ }
+ if (!bitmap.tryAllocPixels(bitmapInfo, factory, colorTable.get())) {
return SkStringPrintf("Image(%s) is too large (%d x %d)", fPath.c_str(),
decodeInfo.width(), decodeInfo.height());
}
@@ -398,6 +429,7 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
return SkStringPrintf("Couldn't getPixels %s.", fPath.c_str());
}
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(bitmap, 0, 0);
break;
}
@@ -432,6 +464,7 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
}
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(bitmap, 0, 0);
break;
}
@@ -487,6 +520,7 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
}
}
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(bitmap, 0, 0);
break;
}
@@ -512,6 +546,7 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
}
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(bitmap, 0, 0);
break;
}
@@ -571,6 +606,7 @@ Error CodecSrc::draw(SkCanvas* canvas) const {
fPath.c_str(), W, H, result);
}
premultiply_if_necessary(subsetBm);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(subsetBm, SkIntToScalar(left), SkIntToScalar(top));
// translate by the scaled height.
top += decodeInfo.height();
@@ -659,7 +695,12 @@ Error AndroidCodecSrc::draw(SkCanvas* canvas) const {
}
SkBitmap bitmap;
- if (!bitmap.tryAllocPixels(decodeInfo, nullptr, colorTable.get())) {
+ SkImageInfo bitmapInfo = decodeInfo;
+ if (kRGBA_8888_SkColorType == decodeInfo.colorType() ||
+ kBGRA_8888_SkColorType == decodeInfo.colorType()) {
+ bitmapInfo = bitmapInfo.makeColorType(kN32_SkColorType);
+ }
+ if (!bitmap.tryAllocPixels(bitmapInfo, nullptr, colorTable.get())) {
return SkStringPrintf("Image(%s) is too large (%d x %d)", fPath.c_str(),
decodeInfo.width(), decodeInfo.height());
}
@@ -681,6 +722,7 @@ Error AndroidCodecSrc::draw(SkCanvas* canvas) const {
return SkStringPrintf("Couldn't getPixels %s.", fPath.c_str());
}
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmap(bitmap, 0, 0);
return "";
}
@@ -739,6 +781,7 @@ Error AndroidCodecSrc::draw(SkCanvas* canvas) const {
SkRect rect = SkRect::MakeXYWH(0, 0, (SkScalar) finalScaledWidth,
(SkScalar) finalScaledHeight);
premultiply_if_necessary(bitmap);
+ swap_rb_if_necessary(bitmap, fDstColorType);
canvas->drawBitmapRect(bitmap, rect, rect, nullptr);
return "";
}
diff --git a/dm/DMSrcSink.h b/dm/DMSrcSink.h
index 743bd1e467..6f4eac71f9 100644
--- a/dm/DMSrcSink.h
+++ b/dm/DMSrcSink.h
@@ -117,6 +117,7 @@ public:
kGetFromCanvas_DstColorType,
kIndex8_Always_DstColorType,
kGrayscale_Always_DstColorType,
+ kNonNative8888_Always_DstColorType,
};
CodecSrc(Path, Mode, DstColorType, SkAlphaType, float);
diff --git a/src/codec/SkBmpRLECodec.cpp b/src/codec/SkBmpRLECodec.cpp
index d80dd1a18a..02b42f6d90 100644
--- a/src/codec/SkBmpRLECodec.cpp
+++ b/src/codec/SkBmpRLECodec.cpp
@@ -70,7 +70,7 @@ SkCodec::Result SkBmpRLECodec::onGetPixels(const SkImageInfo& dstInfo,
/*
* Process the color table for the bmp input
*/
- bool SkBmpRLECodec::createColorTable(int* numColors) {
+ bool SkBmpRLECodec::createColorTable(SkColorType dstColorType, int* numColors) {
// Allocate memory for color table
uint32_t colorBytes = 0;
SkPMColor colorTable[256];
@@ -96,12 +96,13 @@ SkCodec::Result SkBmpRLECodec::onGetPixels(const SkImageInfo& dstInfo,
}
// Fill in the color table
+ PackColorProc packARGB = choose_pack_color_proc(false, dstColorType);
uint32_t i = 0;
for (; i < numColorsToRead; i++) {
uint8_t blue = get_byte(cBuffer.get(), i*fBytesPerColor);
uint8_t green = get_byte(cBuffer.get(), i*fBytesPerColor + 1);
uint8_t red = get_byte(cBuffer.get(), i*fBytesPerColor + 2);
- colorTable[i] = SkPackARGB32NoCheck(0xFF, red, green, blue);
+ colorTable[i] = packARGB(0xFF, red, green, blue);
}
// To avoid segmentation faults on bad pixel data, fill the end of the
@@ -208,7 +209,8 @@ void SkBmpRLECodec::setPixel(void* dst, size_t dstRowBytes,
// Set the pixel based on destination color type
const int dstX = get_dst_coord(x, fSampleX);
switch (dstInfo.colorType()) {
- case kN32_SkColorType: {
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType: {
SkPMColor* dstRow = SkTAddOffset<SkPMColor>(dst, row * (int) dstRowBytes);
dstRow[dstX] = fColorTable->operator[](index);
break;
@@ -241,9 +243,14 @@ void SkBmpRLECodec::setRGBPixel(void* dst, size_t dstRowBytes,
// Set the pixel based on destination color type
const int dstX = get_dst_coord(x, fSampleX);
switch (dstInfo.colorType()) {
- case kN32_SkColorType: {
+ case kRGBA_8888_SkColorType: {
SkPMColor* dstRow = SkTAddOffset<SkPMColor>(dst, row * (int) dstRowBytes);
- dstRow[dstX] = SkPackARGB32NoCheck(0xFF, red, green, blue);
+ dstRow[dstX] = SkPackARGB_as_RGBA(0xFF, red, green, blue);
+ break;
+ }
+ case kBGRA_8888_SkColorType: {
+ SkPMColor* dstRow = SkTAddOffset<SkPMColor>(dst, row * (int) dstRowBytes);
+ dstRow[dstX] = SkPackARGB_as_BGRA(0xFF, red, green, blue);
break;
}
case kRGB_565_SkColorType: {
@@ -275,7 +282,7 @@ SkCodec::Result SkBmpRLECodec::prepareToDecode(const SkImageInfo& dstInfo,
// Create the color table if necessary and prepare the stream for decode
// Note that if it is non-NULL, inputColorCount will be modified
- if (!this->createColorTable(inputColorCount)) {
+ if (!this->createColorTable(dstInfo.colorType(), inputColorCount)) {
SkCodecPrintf("Error: could not create color table.\n");
return SkCodec::kInvalidInput;
}
@@ -315,7 +322,8 @@ int SkBmpRLECodec::decodeRows(const SkImageInfo& info, void* dst, size_t dstRowB
// the skipped pixels will be transparent.
// Because of the need for transparent pixels, kN32 is the only color
// type that makes sense for the destination format.
- SkASSERT(kN32_SkColorType == dstInfo.colorType());
+ SkASSERT(kRGBA_8888_SkColorType == dstInfo.colorType() ||
+ kBGRA_8888_SkColorType == dstInfo.colorType());
if (dst) {
SkSampler::Fill(dstInfo, dst, dstRowBytes, SK_ColorTRANSPARENT, opts.fZeroInitialized);
}
diff --git a/src/codec/SkBmpRLECodec.h b/src/codec/SkBmpRLECodec.h
index e0afccd927..c5236a8100 100644
--- a/src/codec/SkBmpRLECodec.h
+++ b/src/codec/SkBmpRLECodec.h
@@ -58,7 +58,7 @@ private:
* Creates the color table
* Sets colorCount to the new color count if it is non-nullptr
*/
- bool createColorTable(int* colorCount);
+ bool createColorTable(SkColorType dstColorType, int* colorCount);
bool initializeStreamBuffer();
diff --git a/src/codec/SkBmpStandardCodec.cpp b/src/codec/SkBmpStandardCodec.cpp
index b2d8fc9735..358da057c6 100644
--- a/src/codec/SkBmpStandardCodec.cpp
+++ b/src/codec/SkBmpStandardCodec.cpp
@@ -68,7 +68,8 @@ SkCodec::Result SkBmpStandardCodec::onGetPixels(const SkImageInfo& dstInfo,
/*
* Process the color table for the bmp input
*/
- bool SkBmpStandardCodec::createColorTable(SkAlphaType dstAlphaType, int* numColors) {
+ bool SkBmpStandardCodec::createColorTable(SkColorType dstColorType, SkAlphaType dstAlphaType,
+ int* numColors) {
// Allocate memory for color table
uint32_t colorBytes = 0;
SkPMColor colorTable[256];
@@ -94,12 +95,8 @@ SkCodec::Result SkBmpStandardCodec::onGetPixels(const SkImageInfo& dstInfo,
}
// Choose the proper packing function
- SkPMColor (*packARGB) (uint32_t, uint32_t, uint32_t, uint32_t);
- if (fIsOpaque || kUnpremul_SkAlphaType == dstAlphaType) {
- packARGB = &SkPackARGB32NoCheck;
- } else {
- packARGB = &SkPremultiplyARGBInline;
- }
+ bool isPremul = (kPremul_SkAlphaType == dstAlphaType) && !fIsOpaque;
+ PackColorProc packARGB = choose_pack_color_proc(isPremul, dstColorType);
// Fill in the color table
uint32_t i = 0;
@@ -174,7 +171,7 @@ SkCodec::Result SkBmpStandardCodec::prepareToDecode(const SkImageInfo& dstInfo,
const SkCodec::Options& options, SkPMColor inputColorPtr[], int* inputColorCount) {
// Create the color table if necessary and prepare the stream for decode
// Note that if it is non-NULL, inputColorCount will be modified
- if (!this->createColorTable(dstInfo.alphaType(), inputColorCount)) {
+ if (!this->createColorTable(dstInfo.colorType(), dstInfo.alphaType(), inputColorCount)) {
SkCodecPrintf("Error: could not create color table.\n");
return SkCodec::kInvalidInput;
}
@@ -263,7 +260,8 @@ void SkBmpStandardCodec::decodeIcoMask(SkStream* stream, const SkImageInfo& dstI
// BMP in ICO have transparency, so this cannot be 565, and this mask
// prevents us from using kIndex8. The below code depends on the output
// being an SkPMColor.
- SkASSERT(dstInfo.colorType() == kN32_SkColorType);
+ SkASSERT(kRGBA_8888_SkColorType == dstInfo.colorType() ||
+ kBGRA_8888_SkColorType == dstInfo.colorType());
// If we are sampling, make sure that we only mask the sampled pixels.
// We do not need to worry about sampling in the y-dimension because that
diff --git a/src/codec/SkBmpStandardCodec.h b/src/codec/SkBmpStandardCodec.h
index b2b53df6c8..506742b05c 100644
--- a/src/codec/SkBmpStandardCodec.h
+++ b/src/codec/SkBmpStandardCodec.h
@@ -70,7 +70,7 @@ private:
* Creates the color table
* Sets colorCount to the new color count if it is non-nullptr
*/
- bool createColorTable(SkAlphaType alphaType, int* colorCount);
+ bool createColorTable(SkColorType colorType, SkAlphaType alphaType, int* colorCount);
void initializeSwizzler(const SkImageInfo& dstInfo, const Options& opts);
diff --git a/src/codec/SkCodecPriv.h b/src/codec/SkCodecPriv.h
index 8dde60fcd3..1694784785 100644
--- a/src/codec/SkCodecPriv.h
+++ b/src/codec/SkCodecPriv.h
@@ -128,7 +128,8 @@ inline bool conversion_possible(const SkImageInfo& dst, const SkImageInfo& src)
// Check for supported color types
switch (dst.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
return true;
case kRGB_565_SkColorType:
return kOpaque_SkAlphaType == dst.alphaType();
@@ -156,7 +157,8 @@ inline uint32_t get_color_table_fill_value(SkColorType colorType, const SkPMColo
uint8_t fillIndex) {
SkASSERT(nullptr != colorPtr);
switch (colorType) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
return colorPtr[fillIndex];
case kRGB_565_SkColorType:
return SkPixel32ToPixel16(colorPtr[fillIndex]);
@@ -271,4 +273,52 @@ inline uint16_t get_endian_short(const uint8_t* data, bool littleEndian) {
return (data[0] << 8) | (data[1]);
}
+inline SkPMColor premultiply_argb_as_rgba(U8CPU a, U8CPU r, U8CPU g, U8CPU b) {
+ if (a != 255) {
+ r = SkMulDiv255Round(r, a);
+ g = SkMulDiv255Round(g, a);
+ b = SkMulDiv255Round(b, a);
+ }
+
+ return SkPackARGB_as_RGBA(a, r, g, b);
+}
+
+inline SkPMColor premultiply_argb_as_bgra(U8CPU a, U8CPU r, U8CPU g, U8CPU b) {
+ if (a != 255) {
+ r = SkMulDiv255Round(r, a);
+ g = SkMulDiv255Round(g, a);
+ b = SkMulDiv255Round(b, a);
+ }
+
+ return SkPackARGB_as_BGRA(a, r, g, b);
+}
+
+inline bool is_rgba(SkColorType colorType) {
+#ifdef SK_PMCOLOR_IS_RGBA
+ return (kBGRA_8888_SkColorType != colorType);
+#else
+ return (kRGBA_8888_SkColorType == colorType);
+#endif
+}
+
+// Method for coverting to a 32 bit pixel.
+typedef uint32_t (*PackColorProc)(U8CPU a, U8CPU r, U8CPU g, U8CPU b);
+
+inline PackColorProc choose_pack_color_proc(bool isPremul, SkColorType colorType) {
+ bool isRGBA = is_rgba(colorType);
+ if (isPremul) {
+ if (isRGBA) {
+ return &premultiply_argb_as_rgba;
+ } else {
+ return &premultiply_argb_as_bgra;
+ }
+ } else {
+ if (isRGBA) {
+ return &SkPackARGB_as_RGBA;
+ } else {
+ return &SkPackARGB_as_BGRA;
+ }
+ }
+}
+
#endif // SkCodecPriv_DEFINED
diff --git a/src/codec/SkGifCodec.cpp b/src/codec/SkGifCodec.cpp
index 774131f648..75e9d63fa7 100644
--- a/src/codec/SkGifCodec.cpp
+++ b/src/codec/SkGifCodec.cpp
@@ -410,8 +410,9 @@ void SkGifCodec::initializeColorTable(const SkImageInfo& dstInfo, SkPMColor* inp
// giflib guarantees these properties
SkASSERT(colorCount == (unsigned) (1 << (colorMap->BitsPerPixel)));
SkASSERT(colorCount <= 256);
+ PackColorProc proc = choose_pack_color_proc(false, dstInfo.colorType());
for (uint32_t i = 0; i < colorCount; i++) {
- colorPtr[i] = SkPackARGB32(0xFF, colorMap->Colors[i].Red,
+ colorPtr[i] = proc(0xFF, colorMap->Colors[i].Red,
colorMap->Colors[i].Green, colorMap->Colors[i].Blue);
}
}
diff --git a/src/codec/SkJpegCodec.cpp b/src/codec/SkJpegCodec.cpp
index 8d32f2b44d..0799e81381 100644
--- a/src/codec/SkJpegCodec.cpp
+++ b/src/codec/SkJpegCodec.cpp
@@ -350,18 +350,23 @@ bool SkJpegCodec::setOutputColorSpace(const SkImageInfo& dst) {
// Check for valid color types and set the output color space
switch (dst.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
if (isCMYK) {
fDecoderMgr->dinfo()->out_color_space = JCS_CMYK;
} else {
#ifdef LIBJPEG_TURBO_VERSION
- // Check the byte ordering of the RGBA color space for the
- // current platform
- #ifdef SK_PMCOLOR_IS_RGBA
fDecoderMgr->dinfo()->out_color_space = JCS_EXT_RGBA;
- #else
+#else
+ fDecoderMgr->dinfo()->out_color_space = JCS_RGB;
+#endif
+ }
+ return true;
+ case kBGRA_8888_SkColorType:
+ if (isCMYK) {
+ fDecoderMgr->dinfo()->out_color_space = JCS_CMYK;
+ } else {
+#ifdef LIBJPEG_TURBO_VERSION
fDecoderMgr->dinfo()->out_color_space = JCS_EXT_BGRA;
- #endif
#else
fDecoderMgr->dinfo()->out_color_space = JCS_RGB;
#endif
diff --git a/src/codec/SkMaskSwizzler.cpp b/src/codec/SkMaskSwizzler.cpp
index 7630a7b59f..2df10ee24c 100644
--- a/src/codec/SkMaskSwizzler.cpp
+++ b/src/codec/SkMaskSwizzler.cpp
@@ -9,7 +9,7 @@
#include "SkColorPriv.h"
#include "SkMaskSwizzler.h"
-static void swizzle_mask16_to_n32_opaque(
+static void swizzle_mask16_to_rgba_opaque(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -21,12 +21,29 @@ static void swizzle_mask16_to_n32_opaque(
uint8_t red = masks->getRed(p);
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
- dstPtr[i] = SkPackARGB32NoCheck(0xFF, red, green, blue);
+ dstPtr[i] = SkPackARGB_as_RGBA(0xFF, red, green, blue);
srcPtr += sampleX;
}
}
-static void swizzle_mask16_to_n32_unpremul(
+static void swizzle_mask16_to_bgra_opaque(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint16_t* srcPtr = ((uint16_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint16_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ dstPtr[i] = SkPackARGB_as_BGRA(0xFF, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask16_to_rgba_unpremul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -39,12 +56,12 @@ static void swizzle_mask16_to_n32_unpremul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPackARGB32NoCheck(alpha, red, green, blue);
+ dstPtr[i] = SkPackARGB_as_RGBA(alpha, red, green, blue);
srcPtr += sampleX;
}
}
-static void swizzle_mask16_to_n32_premul(
+static void swizzle_mask16_to_bgra_unpremul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -57,7 +74,43 @@ static void swizzle_mask16_to_n32_premul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPreMultiplyARGB(alpha, red, green, blue);
+ dstPtr[i] = SkPackARGB_as_BGRA(alpha, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask16_to_rgba_premul(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint16_t* srcPtr = ((uint16_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint16_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = premultiply_argb_as_rgba(alpha, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask16_to_bgra_premul(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint16_t* srcPtr = ((uint16_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint16_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = premultiply_argb_as_bgra(alpha, red, green, blue);
srcPtr += sampleX;
}
}
@@ -81,7 +134,41 @@ static void swizzle_mask16_to_565(
}
}
-static void swizzle_mask24_to_n32_opaque(
+static void swizzle_mask24_to_rgba_opaque(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ srcRow += 3 * startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcRow[0] | (srcRow[1] << 8) | srcRow[2] << 16;
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ dstPtr[i] = SkPackARGB_as_RGBA(0xFF, red, green, blue);
+ srcRow += 3 * sampleX;
+ }
+}
+
+static void swizzle_mask24_to_bgra_opaque(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ srcRow += 3 * startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcRow[0] | (srcRow[1] << 8) | srcRow[2] << 16;
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ dstPtr[i] = SkPackARGB_as_BGRA(0xFF, red, green, blue);
+ srcRow += 3 * sampleX;
+ }
+}
+
+static void swizzle_mask24_to_rgba_unpremul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -93,12 +180,13 @@ static void swizzle_mask24_to_n32_opaque(
uint8_t red = masks->getRed(p);
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
- dstPtr[i] = SkPackARGB32NoCheck(0xFF, red, green, blue);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = SkPackARGB_as_RGBA(alpha, red, green, blue);
srcRow += 3 * sampleX;
}
}
-static void swizzle_mask24_to_n32_unpremul(
+static void swizzle_mask24_to_bgra_unpremul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -111,12 +199,12 @@ static void swizzle_mask24_to_n32_unpremul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPackARGB32NoCheck(alpha, red, green, blue);
+ dstPtr[i] = SkPackARGB_as_BGRA(alpha, red, green, blue);
srcRow += 3 * sampleX;
}
}
-static void swizzle_mask24_to_n32_premul(
+static void swizzle_mask24_to_rgba_premul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -129,7 +217,25 @@ static void swizzle_mask24_to_n32_premul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPreMultiplyARGB(alpha, red, green, blue);
+ dstPtr[i] = premultiply_argb_as_rgba(alpha, red, green, blue);
+ srcRow += 3 * sampleX;
+ }
+}
+
+static void swizzle_mask24_to_bgra_premul(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ srcRow += 3 * startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcRow[0] | (srcRow[1] << 8) | srcRow[2] << 16;
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = premultiply_argb_as_bgra(alpha, red, green, blue);
srcRow += 3 * sampleX;
}
}
@@ -151,7 +257,59 @@ static void swizzle_mask24_to_565(
}
}
-static void swizzle_mask32_to_n32_opaque(
+static void swizzle_mask32_to_rgba_opaque(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint32_t* srcPtr = ((uint32_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ dstPtr[i] = SkPackARGB_as_RGBA(0xFF, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask32_to_bgra_opaque(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint32_t* srcPtr = ((uint32_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ dstPtr[i] = SkPackARGB_as_BGRA(0xFF, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask32_to_rgba_unpremul(
+ void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
+ uint32_t startX, uint32_t sampleX) {
+
+ // Use the masks to decode to the destination
+ uint32_t* srcPtr = ((uint32_t*) srcRow) + startX;
+ SkPMColor* dstPtr = (SkPMColor*) dstRow;
+ for (int i = 0; i < width; i++) {
+ uint32_t p = srcPtr[0];
+ uint8_t red = masks->getRed(p);
+ uint8_t green = masks->getGreen(p);
+ uint8_t blue = masks->getBlue(p);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = SkPackARGB_as_RGBA(alpha, red, green, blue);
+ srcPtr += sampleX;
+ }
+}
+
+static void swizzle_mask32_to_bgra_unpremul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -163,12 +321,13 @@ static void swizzle_mask32_to_n32_opaque(
uint8_t red = masks->getRed(p);
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
- dstPtr[i] = SkPackARGB32NoCheck(0xFF, red, green, blue);
+ uint8_t alpha = masks->getAlpha(p);
+ dstPtr[i] = SkPackARGB_as_BGRA(alpha, red, green, blue);
srcPtr += sampleX;
}
}
-static void swizzle_mask32_to_n32_unpremul(
+static void swizzle_mask32_to_rgba_premul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -181,12 +340,12 @@ static void swizzle_mask32_to_n32_unpremul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPackARGB32NoCheck(alpha, red, green, blue);
+ dstPtr[i] = premultiply_argb_as_rgba(alpha, red, green, blue);
srcPtr += sampleX;
}
}
-static void swizzle_mask32_to_n32_premul(
+static void swizzle_mask32_to_bgra_premul(
void* dstRow, const uint8_t* srcRow, int width, SkMasks* masks,
uint32_t startX, uint32_t sampleX) {
@@ -199,7 +358,7 @@ static void swizzle_mask32_to_n32_premul(
uint8_t green = masks->getGreen(p);
uint8_t blue = masks->getBlue(p);
uint8_t alpha = masks->getAlpha(p);
- dstPtr[i] = SkPreMultiplyARGB(alpha, red, green, blue);
+ dstPtr[i] = premultiply_argb_as_bgra(alpha, red, green, blue);
srcPtr += sampleX;
}
}
@@ -234,16 +393,32 @@ SkMaskSwizzler* SkMaskSwizzler::CreateMaskSwizzler(const SkImageInfo& dstInfo,
switch (bitsPerPixel) {
case 16:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
+ proc = &swizzle_mask16_to_rgba_opaque;
+ } else {
+ switch (dstInfo.alphaType()) {
+ case kUnpremul_SkAlphaType:
+ proc = &swizzle_mask16_to_rgba_unpremul;
+ break;
+ case kPremul_SkAlphaType:
+ proc = &swizzle_mask16_to_rgba_premul;
+ break;
+ default:
+ break;
+ }
+ }
+ break;
+ case kBGRA_8888_SkColorType:
if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
- proc = &swizzle_mask16_to_n32_opaque;
+ proc = &swizzle_mask16_to_bgra_opaque;
} else {
switch (dstInfo.alphaType()) {
case kUnpremul_SkAlphaType:
- proc = &swizzle_mask16_to_n32_unpremul;
+ proc = &swizzle_mask16_to_bgra_unpremul;
break;
case kPremul_SkAlphaType:
- proc = &swizzle_mask16_to_n32_premul;
+ proc = &swizzle_mask16_to_bgra_premul;
break;
default:
break;
@@ -259,16 +434,32 @@ SkMaskSwizzler* SkMaskSwizzler::CreateMaskSwizzler(const SkImageInfo& dstInfo,
break;
case 24:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
+ proc = &swizzle_mask24_to_rgba_opaque;
+ } else {
+ switch (dstInfo.alphaType()) {
+ case kUnpremul_SkAlphaType:
+ proc = &swizzle_mask24_to_rgba_unpremul;
+ break;
+ case kPremul_SkAlphaType:
+ proc = &swizzle_mask24_to_rgba_premul;
+ break;
+ default:
+ break;
+ }
+ }
+ break;
+ case kBGRA_8888_SkColorType:
if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
- proc = &swizzle_mask24_to_n32_opaque;
+ proc = &swizzle_mask24_to_bgra_opaque;
} else {
switch (dstInfo.alphaType()) {
case kUnpremul_SkAlphaType:
- proc = &swizzle_mask24_to_n32_unpremul;
+ proc = &swizzle_mask24_to_bgra_unpremul;
break;
case kPremul_SkAlphaType:
- proc = &swizzle_mask24_to_n32_premul;
+ proc = &swizzle_mask24_to_bgra_premul;
break;
default:
break;
@@ -284,16 +475,32 @@ SkMaskSwizzler* SkMaskSwizzler::CreateMaskSwizzler(const SkImageInfo& dstInfo,
break;
case 32:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
+ proc = &swizzle_mask32_to_rgba_opaque;
+ } else {
+ switch (dstInfo.alphaType()) {
+ case kUnpremul_SkAlphaType:
+ proc = &swizzle_mask32_to_rgba_unpremul;
+ break;
+ case kPremul_SkAlphaType:
+ proc = &swizzle_mask32_to_rgba_premul;
+ break;
+ default:
+ break;
+ }
+ }
+ break;
+ case kBGRA_8888_SkColorType:
if (kOpaque_SkAlphaType == srcInfo.alphaType()) {
- proc = &swizzle_mask32_to_n32_opaque;
+ proc = &swizzle_mask32_to_bgra_opaque;
} else {
switch (dstInfo.alphaType()) {
case kUnpremul_SkAlphaType:
- proc = &swizzle_mask32_to_n32_unpremul;
+ proc = &swizzle_mask32_to_bgra_unpremul;
break;
case kPremul_SkAlphaType:
- proc = &swizzle_mask32_to_n32_premul;
+ proc = &swizzle_mask32_to_bgra_premul;
break;
default:
break;
diff --git a/src/codec/SkPngCodec.cpp b/src/codec/SkPngCodec.cpp
index 240902de30..a5ff9fcc96 100644
--- a/src/codec/SkPngCodec.cpp
+++ b/src/codec/SkPngCodec.cpp
@@ -86,14 +86,10 @@ private:
};
#define AutoCleanPng(...) SK_REQUIRE_LOCAL_VAR(AutoCleanPng)
-// Method for coverting to either an SkPMColor or a similarly packed
-// unpremultiplied color.
-typedef uint32_t (*PackColorProc)(U8CPU a, U8CPU r, U8CPU g, U8CPU b);
-
// Note: SkColorTable claims to store SkPMColors, which is not necessarily
// the case here.
// TODO: If we add support for non-native swizzles, we'll need to handle that here.
-bool SkPngCodec::decodePalette(bool premultiply, int* ctableCount) {
+bool SkPngCodec::createColorTable(SkColorType dstColorType, bool premultiply, int* ctableCount) {
int numColors;
png_color* palette;
@@ -109,12 +105,7 @@ bool SkPngCodec::decodePalette(bool premultiply, int* ctableCount) {
if (png_get_tRNS(fPng_ptr, fInfo_ptr, &alphas, &numColorsWithAlpha, nullptr)) {
// Choose which function to use to create the color table. If the final destination's
// colortype is unpremultiplied, the color table will store unpremultiplied colors.
- PackColorProc proc;
- if (premultiply) {
- proc = &SkPremultiplyARGBInline;
- } else {
- proc = &SkPackARGB32NoCheck;
- }
+ PackColorProc proc = choose_pack_color_proc(premultiply, dstColorType);
for (int i = 0; i < numColorsWithAlpha; i++) {
// We don't have a function in SkOpts that combines a set of alphas with a set
@@ -134,11 +125,13 @@ bool SkPngCodec::decodePalette(bool premultiply, int* ctableCount) {
SkASSERT(&palette->green < &palette->blue);
#endif
-#ifdef SK_PMCOLOR_IS_RGBA
- SkOpts::RGB_to_RGB1(colorPtr + numColorsWithAlpha, palette, numColors - numColorsWithAlpha);
-#else
- SkOpts::RGB_to_BGR1(colorPtr + numColorsWithAlpha, palette, numColors - numColorsWithAlpha);
-#endif
+ if (is_rgba(dstColorType)) {
+ SkOpts::RGB_to_RGB1(colorPtr + numColorsWithAlpha, palette,
+ numColors - numColorsWithAlpha);
+ } else {
+ SkOpts::RGB_to_BGR1(colorPtr + numColorsWithAlpha, palette,
+ numColors - numColorsWithAlpha);
+ }
}
// Pad the color table with the last color in the table (or black) in the case that
@@ -474,7 +467,8 @@ SkCodec::Result SkPngCodec::initializeSwizzler(const SkImageInfo& requestedInfo,
png_read_update_info(fPng_ptr, fInfo_ptr);
if (SkEncodedInfo::kPalette_Color == this->getEncodedInfo().color()) {
- if (!this->decodePalette(kPremul_SkAlphaType == requestedInfo.alphaType(), ctableCount)) {
+ if (!this->createColorTable(requestedInfo.colorType(),
+ kPremul_SkAlphaType == requestedInfo.alphaType(), ctableCount)) {
return kInvalidInput;
}
}
diff --git a/src/codec/SkPngCodec.h b/src/codec/SkPngCodec.h
index 934513a676..0a8878395a 100644
--- a/src/codec/SkPngCodec.h
+++ b/src/codec/SkPngCodec.h
@@ -60,7 +60,7 @@ private:
const int fNumberPasses;
int fBitDepth;
- bool decodePalette(bool premultiply, int* ctableCount);
+ bool createColorTable(SkColorType dstColorType, bool premultiply, int* ctableCount);
void destroyReadStruct();
typedef SkCodec INHERITED;
diff --git a/src/codec/SkSampler.cpp b/src/codec/SkSampler.cpp
index c69d003c0f..ccfe400ec9 100644
--- a/src/codec/SkSampler.cpp
+++ b/src/codec/SkSampler.cpp
@@ -21,7 +21,8 @@ void SkSampler::Fill(const SkImageInfo& info, void* dst, size_t rowBytes,
// Use the proper memset routine to fill the remaining bytes
switch (info.colorType()) {
- case kN32_SkColorType: {
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType: {
// If memory is zero initialized, we may not need to fill
uint32_t color = colorOrIndex;
if (SkCodec::kYes_ZeroInitialized == zeroInit && 0 == color) {
diff --git a/src/codec/SkSwizzler.cpp b/src/codec/SkSwizzler.cpp
index a4b30287c2..f242421424 100644
--- a/src/codec/SkSwizzler.cpp
+++ b/src/codec/SkSwizzler.cpp
@@ -348,21 +348,9 @@ static void fast_swizzle_grayalpha_to_n32_premul(
SkOpts::grayA_to_rgbA((uint32_t*) dst, src + offset, width);
}
-// kBGRX
+// kBGR
-static void swizzle_bgrx_to_n32(
- void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
- int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
-
- src += offset;
- SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
- for (int x = 0; x < dstWidth; x++) {
- dst[x] = SkPackARGB32NoCheck(0xFF, src[2], src[1], src[0]);
- src += deltaSrc;
- }
-}
-
-static void swizzle_bgrx_to_565(
+static void swizzle_bgr_to_565(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
@@ -374,79 +362,44 @@ static void swizzle_bgrx_to_565(
}
}
-// kBGRA
+// kRGB
-static void swizzle_bgra_to_n32_unpremul(
+static void swizzle_rgb_to_rgba(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
src += offset;
SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
for (int x = 0; x < dstWidth; x++) {
- uint8_t alpha = src[3];
- dst[x] = SkPackARGB32NoCheck(alpha, src[2], src[1], src[0]);
+ dst[x] = SkPackARGB_as_RGBA(0xFF, src[0], src[1], src[2]);
src += deltaSrc;
}
}
-static void fast_swizzle_bgra_to_n32_unpremul(
- void* dst, const uint8_t* src, int width, int bpp, int deltaSrc, int offset,
- const SkPMColor ctable[]) {
-
- // This function must not be called if we are sampling. If we are not
- // sampling, deltaSrc should equal bpp.
- SkASSERT(deltaSrc == bpp);
-
-#ifdef SK_PMCOLOR_IS_RGBA
- SkOpts::RGBA_to_BGRA((uint32_t*) dst, src + offset, width);
-#else
- memcpy(dst, src + offset, width * bpp);
-#endif
-}
-
-static void swizzle_bgra_to_n32_premul(
+static void swizzle_rgb_to_bgra(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
src += offset;
SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
for (int x = 0; x < dstWidth; x++) {
- uint8_t alpha = src[3];
- dst[x] = SkPremultiplyARGBInline(alpha, src[2], src[1], src[0]);
+ dst[x] = SkPackARGB_as_BGRA(0xFF, src[0], src[1], src[2]);
src += deltaSrc;
}
}
-static void fast_swizzle_bgra_to_n32_premul(
- void* dst, const uint8_t* src, int width, int bpp, int deltaSrc, int offset,
- const SkPMColor ctable[]) {
+static void fast_swizzle_rgb_to_rgba(
+ void* dst, const uint8_t* src, int width, int bpp, int deltaSrc,
+ int offset, const SkPMColor ctable[]) {
// This function must not be called if we are sampling. If we are not
// sampling, deltaSrc should equal bpp.
SkASSERT(deltaSrc == bpp);
-#ifdef SK_PMCOLOR_IS_RGBA
- SkOpts::RGBA_to_bgrA((uint32_t*) dst, src + offset, width);
-#else
- SkOpts::RGBA_to_rgbA((uint32_t*) dst, src + offset, width);
-#endif
-}
-
-// kRGB
-
-static void swizzle_rgb_to_n32(
- void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
- int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
-
- src += offset;
- SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
- for (int x = 0; x < dstWidth; x++) {
- dst[x] = SkPackARGB32NoCheck(0xFF, src[0], src[1], src[2]);
- src += deltaSrc;
- }
+ SkOpts::RGB_to_RGB1((uint32_t*) dst, src + offset, width);
}
-static void fast_swizzle_rgb_to_n32(
+static void fast_swizzle_rgb_to_bgra(
void* dst, const uint8_t* src, int width, int bpp, int deltaSrc,
int offset, const SkPMColor ctable[]) {
@@ -454,11 +407,7 @@ static void fast_swizzle_rgb_to_n32(
// sampling, deltaSrc should equal bpp.
SkASSERT(deltaSrc == bpp);
-#ifdef SK_PMCOLOR_IS_RGBA
- SkOpts::RGB_to_RGB1((uint32_t*) dst, src + offset, width);
-#else
SkOpts::RGB_to_BGR1((uint32_t*) dst, src + offset, width);
-#endif
}
static void swizzle_rgb_to_565(
@@ -475,20 +424,31 @@ static void swizzle_rgb_to_565(
// kRGBA
-static void swizzle_rgba_to_n32_premul(
+static void swizzle_rgba_to_rgba_premul(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
src += offset;
SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
for (int x = 0; x < dstWidth; x++) {
- unsigned alpha = src[3];
- dst[x] = SkPremultiplyARGBInline(alpha, src[0], src[1], src[2]);
+ dst[x] = premultiply_argb_as_rgba(src[3], src[0], src[1], src[2]);
+ src += deltaSrc;
+ }
+}
+
+static void swizzle_rgba_to_bgra_premul(
+ void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
+ int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
+
+ src += offset;
+ SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
+ for (int x = 0; x < dstWidth; x++) {
+ dst[x] = premultiply_argb_as_bgra(src[3], src[0], src[1], src[2]);
src += deltaSrc;
}
}
-static void fast_swizzle_rgba_to_n32_premul(
+static void fast_swizzle_rgba_to_rgba_premul(
void* dst, const uint8_t* src, int width, int bpp, int deltaSrc,
int offset, const SkPMColor ctable[]) {
@@ -496,14 +456,21 @@ static void fast_swizzle_rgba_to_n32_premul(
// sampling, deltaSrc should equal bpp.
SkASSERT(deltaSrc == bpp);
-#ifdef SK_PMCOLOR_IS_RGBA
SkOpts::RGBA_to_rgbA((uint32_t*) dst, src + offset, width);
-#else
+}
+
+static void fast_swizzle_rgba_to_bgra_premul(
+ void* dst, const uint8_t* src, int width, int bpp, int deltaSrc,
+ int offset, const SkPMColor ctable[]) {
+
+ // This function must not be called if we are sampling. If we are not
+ // sampling, deltaSrc should equal bpp.
+ SkASSERT(deltaSrc == bpp);
+
SkOpts::RGBA_to_bgrA((uint32_t*) dst, src + offset, width);
-#endif
}
-static void swizzle_rgba_to_n32_unpremul(
+static void swizzle_rgba_to_bgra_unpremul(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
@@ -511,12 +478,12 @@ static void swizzle_rgba_to_n32_unpremul(
uint32_t* SK_RESTRICT dst = reinterpret_cast<uint32_t*>(dstRow);
for (int x = 0; x < dstWidth; x++) {
unsigned alpha = src[3];
- dst[x] = SkPackARGB32NoCheck(alpha, src[0], src[1], src[2]);
+ dst[x] = SkPackARGB_as_BGRA(alpha, src[0], src[1], src[2]);
src += deltaSrc;
}
}
-static void fast_swizzle_rgba_to_n32_unpremul(
+static void fast_swizzle_rgba_to_bgra_unpremul(
void* dst, const uint8_t* src, int width, int bpp, int deltaSrc, int offset,
const SkPMColor ctable[]) {
@@ -524,11 +491,7 @@ static void fast_swizzle_rgba_to_n32_unpremul(
// sampling, deltaSrc should equal bpp.
SkASSERT(deltaSrc == bpp);
-#ifdef SK_PMCOLOR_IS_RGBA
- memcpy(dst, src + offset, width * bpp);
-#else
SkOpts::RGBA_to_BGRA((uint32_t*) dst, src + offset, width);
-#endif
}
// kCMYK
@@ -576,7 +539,23 @@ static void fast_swizzle_rgba_to_n32_unpremul(
// R = C * K / 255
// G = M * K / 255
// B = Y * K / 255
-static void swizzle_cmyk_to_n32(
+static void swizzle_cmyk_to_rgba(
+ void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
+ int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
+
+ src += offset;
+ SkPMColor* SK_RESTRICT dst = (SkPMColor*)dstRow;
+ for (int x = 0; x < dstWidth; x++) {
+ const uint8_t r = SkMulDiv255Round(src[0], src[3]);
+ const uint8_t g = SkMulDiv255Round(src[1], src[3]);
+ const uint8_t b = SkMulDiv255Round(src[2], src[3]);
+
+ dst[x] = SkPackARGB_as_RGBA(0xFF, r, g, b);
+ src += deltaSrc;
+ }
+}
+
+static void swizzle_cmyk_to_bgra(
void* SK_RESTRICT dstRow, const uint8_t* SK_RESTRICT src, int dstWidth,
int bpp, int deltaSrc, int offset, const SkPMColor ctable[]) {
@@ -587,12 +566,12 @@ static void swizzle_cmyk_to_n32(
const uint8_t g = SkMulDiv255Round(src[1], src[3]);
const uint8_t b = SkMulDiv255Round(src[2], src[3]);
- dst[x] = SkPackARGB32NoCheck(0xFF, r, g, b);
+ dst[x] = SkPackARGB_as_BGRA(0xFF, r, g, b);
src += deltaSrc;
}
}
-static void fast_swizzle_cmyk_to_n32(
+static void fast_swizzle_cmyk_to_rgba(
void* dst, const uint8_t* src, int width, int bpp, int deltaSrc, int offset,
const SkPMColor ctable[]) {
@@ -600,11 +579,18 @@ static void fast_swizzle_cmyk_to_n32(
// sampling, deltaSrc should equal bpp.
SkASSERT(deltaSrc == bpp);
-#ifdef SK_PMCOLOR_IS_RGBA
SkOpts::inverted_CMYK_to_RGB1((uint32_t*) dst, src + offset, width);
-#else
+}
+
+static void fast_swizzle_cmyk_to_bgra(
+ void* dst, const uint8_t* src, int width, int bpp, int deltaSrc, int offset,
+ const SkPMColor ctable[]) {
+
+ // This function must not be called if we are sampling. If we are not
+ // sampling, deltaSrc should equal bpp.
+ SkASSERT(deltaSrc == bpp);
+
SkOpts::inverted_CMYK_to_BGR1((uint32_t*) dst, src + offset, width);
-#endif
}
static void swizzle_cmyk_to_565(
@@ -680,7 +666,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
switch (encodedInfo.bitsPerComponent()) {
case 1:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
proc = &swizzle_bit_to_n32;
break;
case kIndex_8_SkColorType:
@@ -698,7 +685,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case 8:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
proc = &swizzle_gray_to_n32;
fastProc = &fast_swizzle_gray_to_n32;
break;
@@ -719,7 +707,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kGrayAlpha_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
if (premultiply) {
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
proc = &SkipLeadingGrayAlphaZerosThen<swizzle_grayalpha_to_n32_premul>;
@@ -753,7 +742,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
case 2:
case 4:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
proc = &swizzle_small_index_to_n32;
break;
case kRGB_565_SkColorType:
@@ -768,7 +758,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case 8:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
proc = &swizzle_index_to_n32_skipZ;
} else {
@@ -792,9 +783,13 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kRGB_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
- proc = &swizzle_rgb_to_n32;
- fastProc = &fast_swizzle_rgb_to_n32;
+ case kRGBA_8888_SkColorType:
+ proc = &swizzle_rgb_to_rgba;
+ fastProc = &fast_swizzle_rgb_to_rgba;
+ break;
+ case kBGRA_8888_SkColorType:
+ proc = &swizzle_rgb_to_bgra;
+ fastProc = &fast_swizzle_rgb_to_bgra;
break;
case kRGB_565_SkColorType:
proc = &swizzle_rgb_to_565;
@@ -805,23 +800,42 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kRGBA_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ if (premultiply) {
+ if (SkCodec::kYes_ZeroInitialized == zeroInit) {
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_rgba_premul>;
+ fastProc = &SkipLeading8888ZerosThen<fast_swizzle_rgba_to_rgba_premul>;
+ } else {
+ proc = &swizzle_rgba_to_rgba_premul;
+ fastProc = &fast_swizzle_rgba_to_rgba_premul;
+ }
+ } else {
+ if (SkCodec::kYes_ZeroInitialized == zeroInit) {
+ proc = &SkipLeading8888ZerosThen<sample4>;
+ fastProc = &SkipLeading8888ZerosThen<copy>;
+ } else {
+ proc = &sample4;
+ fastProc = &copy;
+ }
+ }
+ break;
+ case kBGRA_8888_SkColorType:
if (premultiply) {
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
- proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_n32_premul>;
- fastProc = &SkipLeading8888ZerosThen<fast_swizzle_rgba_to_n32_premul>;
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_bgra_premul>;
+ fastProc = &SkipLeading8888ZerosThen<fast_swizzle_rgba_to_bgra_premul>;
} else {
- proc = &swizzle_rgba_to_n32_premul;
- fastProc = &fast_swizzle_rgba_to_n32_premul;
+ proc = &swizzle_rgba_to_bgra_premul;
+ fastProc = &fast_swizzle_rgba_to_bgra_premul;
}
} else {
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
- proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_n32_unpremul>;
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_bgra_unpremul>;
fastProc = &SkipLeading8888ZerosThen
- <fast_swizzle_rgba_to_n32_unpremul>;
+ <fast_swizzle_rgba_to_bgra_unpremul>;
} else {
- proc = &swizzle_rgba_to_n32_unpremul;
- fastProc = &fast_swizzle_rgba_to_n32_unpremul;
+ proc = &swizzle_rgba_to_bgra_unpremul;
+ fastProc = &fast_swizzle_rgba_to_bgra_unpremul;
}
}
break;
@@ -831,11 +845,16 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kBGR_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
- proc = &swizzle_bgrx_to_n32;
+ case kBGRA_8888_SkColorType:
+ proc = &swizzle_rgb_to_rgba;
+ fastProc = &fast_swizzle_rgb_to_rgba;
+ break;
+ case kRGBA_8888_SkColorType:
+ proc = &swizzle_rgb_to_bgra;
+ fastProc = &fast_swizzle_rgb_to_bgra;
break;
case kRGB_565_SkColorType:
- proc = &swizzle_bgrx_to_565;
+ proc = &swizzle_bgr_to_565;
break;
default:
return nullptr;
@@ -843,11 +862,14 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kBGRX_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
- proc = &swizzle_bgrx_to_n32;
+ case kBGRA_8888_SkColorType:
+ proc = &swizzle_rgb_to_rgba;
+ break;
+ case kRGBA_8888_SkColorType:
+ proc = &swizzle_rgb_to_bgra;
break;
case kRGB_565_SkColorType:
- proc = &swizzle_bgrx_to_565;
+ proc = &swizzle_bgr_to_565;
break;
default:
return nullptr;
@@ -855,23 +877,42 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kBGRA_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
+ case kBGRA_8888_SkColorType:
+ if (premultiply) {
+ if (SkCodec::kYes_ZeroInitialized == zeroInit) {
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_rgba_premul>;
+ fastProc = &SkipLeading8888ZerosThen<fast_swizzle_rgba_to_rgba_premul>;
+ } else {
+ proc = &swizzle_rgba_to_rgba_premul;
+ fastProc = &fast_swizzle_rgba_to_rgba_premul;
+ }
+ } else {
+ if (SkCodec::kYes_ZeroInitialized == zeroInit) {
+ proc = &SkipLeading8888ZerosThen<sample4>;
+ fastProc = &SkipLeading8888ZerosThen<copy>;
+ } else {
+ proc = &sample4;
+ fastProc = &copy;
+ }
+ }
+ break;
+ case kRGBA_8888_SkColorType:
if (premultiply) {
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
- proc = &SkipLeading8888ZerosThen<swizzle_bgra_to_n32_premul>;
- fastProc = &SkipLeading8888ZerosThen<fast_swizzle_bgra_to_n32_premul>;
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_bgra_premul>;
+ fastProc = &SkipLeading8888ZerosThen<fast_swizzle_rgba_to_bgra_premul>;
} else {
- proc = &swizzle_bgra_to_n32_premul;
- fastProc = &fast_swizzle_bgra_to_n32_premul;
+ proc = &swizzle_rgba_to_bgra_premul;
+ fastProc = &fast_swizzle_rgba_to_bgra_premul;
}
} else {
if (SkCodec::kYes_ZeroInitialized == zeroInit) {
- proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_n32_unpremul>;
+ proc = &SkipLeading8888ZerosThen<swizzle_rgba_to_bgra_unpremul>;
fastProc = &SkipLeading8888ZerosThen
- <fast_swizzle_bgra_to_n32_unpremul>;
+ <fast_swizzle_rgba_to_bgra_unpremul>;
} else {
- proc = &swizzle_bgra_to_n32_unpremul;
- fastProc = &fast_swizzle_bgra_to_n32_unpremul;
+ proc = &swizzle_rgba_to_bgra_unpremul;
+ fastProc = &fast_swizzle_rgba_to_bgra_unpremul;
}
}
break;
@@ -881,9 +922,13 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
break;
case SkEncodedInfo::kInvertedCMYK_Color:
switch (dstInfo.colorType()) {
- case kN32_SkColorType:
- proc = &swizzle_cmyk_to_n32;
- fastProc = &fast_swizzle_cmyk_to_n32;
+ case kRGBA_8888_SkColorType:
+ proc = &swizzle_cmyk_to_rgba;
+ fastProc = &fast_swizzle_cmyk_to_rgba;
+ break;
+ case kBGRA_8888_SkColorType:
+ proc = &swizzle_cmyk_to_bgra;
+ fastProc = &fast_swizzle_cmyk_to_bgra;
break;
case kRGB_565_SkColorType:
proc = &swizzle_cmyk_to_565;
@@ -902,7 +947,8 @@ SkSwizzler* SkSwizzler::CreateSwizzler(const SkEncodedInfo& encodedInfo,
proc = &sample2;
fastProc = &copy;
break;
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
proc = &sample4;
fastProc = &copy;
break;
diff --git a/src/codec/SkWbmpCodec.cpp b/src/codec/SkWbmpCodec.cpp
index 1e165b4e1d..527565f6ab 100644
--- a/src/codec/SkWbmpCodec.cpp
+++ b/src/codec/SkWbmpCodec.cpp
@@ -32,7 +32,8 @@ static inline void setup_color_table(SkColorType colorType,
static inline bool valid_color_type(SkColorType colorType, SkAlphaType alphaType) {
switch (colorType) {
- case kN32_SkColorType:
+ case kRGBA_8888_SkColorType:
+ case kBGRA_8888_SkColorType:
case kIndex_8_SkColorType:
return true;
case kGray_8_SkColorType: