2020-08-05 14:44:17 +00:00
|
|
|
/*
|
|
|
|
* Copyright 2020 Google LLC
|
|
|
|
*
|
|
|
|
* Use of this source code is governed by a BSD-style license that can be
|
|
|
|
* found in the LICENSE file.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include "include/core/SkTypes.h"
|
2020-08-05 20:51:10 +00:00
|
|
|
#ifdef SK_ENABLE_NDK_IMAGES
|
2022-04-29 14:02:26 +00:00
|
|
|
#include "include/core/SkColorSpace.h"
|
2020-08-05 14:44:17 +00:00
|
|
|
#include "include/ports/SkImageGeneratorNDK.h"
|
|
|
|
#include "tests/Test.h"
|
|
|
|
#include "tools/Resources.h"
|
2020-08-05 20:51:10 +00:00
|
|
|
#include "tools/ToolUtils.h"
|
2020-08-05 14:44:17 +00:00
|
|
|
|
|
|
|
#include <vector>
|
|
|
|
|
|
|
|
static std::unique_ptr<SkImageGenerator> make_generator(const char* path, skiatest::Reporter* r) {
|
|
|
|
auto data = GetResourceAsData(path);
|
|
|
|
if (data) {
|
|
|
|
auto gen = SkImageGeneratorNDK::MakeFromEncodedNDK(std::move(data));
|
|
|
|
if (gen) {
|
|
|
|
return gen;
|
|
|
|
}
|
|
|
|
ERRORF(r, "Failed to create NDK generator from %s\n", path);
|
|
|
|
} else {
|
|
|
|
// Silently fail so developers can skip using --resources
|
|
|
|
}
|
|
|
|
return nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode, r) {
|
|
|
|
static const struct {
|
|
|
|
const char* fPath;
|
|
|
|
SkISize fSize;
|
|
|
|
} recs[] = {
|
|
|
|
{"images/CMYK.jpg", {642, 516}},
|
|
|
|
{"images/arrow.png", {187, 312}},
|
|
|
|
{"images/baby_tux.webp", {386, 395}},
|
|
|
|
{"images/color_wheel.gif", {128, 128}},
|
|
|
|
{"images/rle.bmp", {320, 240}},
|
|
|
|
{"images/color_wheel.ico", {128, 128}},
|
|
|
|
{"images/google_chrome.ico", {256, 256}},
|
|
|
|
{"images/mandrill.wbmp", {512, 512}},
|
|
|
|
};
|
|
|
|
for (auto& rec : recs) {
|
|
|
|
auto gen = make_generator(rec.fPath, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
const auto& info = gen->getInfo();
|
|
|
|
REPORTER_ASSERT(r, info.dimensions() == rec.fSize);
|
|
|
|
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
|
|
|
|
REPORTER_ASSERT(r, info.alphaType() != kUnpremul_SkAlphaType);
|
|
|
|
auto unpremulInfo = info.makeAlphaType(kUnpremul_SkAlphaType);
|
|
|
|
bm.allocPixels(unpremulInfo);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_nullData, r) {
|
|
|
|
auto gen = SkImageGeneratorNDK::MakeFromEncodedNDK(nullptr);
|
|
|
|
REPORTER_ASSERT(r, !gen);
|
|
|
|
}
|
|
|
|
|
|
|
|
static constexpr skcms_TransferFunction k2Dot6 = {2.6f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f};
|
|
|
|
|
|
|
|
static constexpr skcms_Matrix3x3 kDCIP3 = {{
|
|
|
|
{0.486143, 0.323835, 0.154234},
|
|
|
|
{0.226676, 0.710327, 0.0629966},
|
|
|
|
{0.000800549, 0.0432385, 0.78275},
|
|
|
|
}};
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_reportedColorSpace, r) {
|
|
|
|
for (sk_sp<SkColorSpace> cs : {
|
|
|
|
sk_sp<SkColorSpace>(nullptr),
|
|
|
|
SkColorSpace::MakeSRGB(),
|
|
|
|
SkColorSpace::MakeSRGBLinear(),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kRec2020, SkNamedGamut::kSRGB),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kRec2020, SkNamedGamut::kRec2020),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kSRGB, SkNamedGamut::kDisplayP3),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::k2Dot2, SkNamedGamut::kAdobeRGB),
|
|
|
|
SkColorSpace::MakeRGB(k2Dot6, kDCIP3),
|
|
|
|
}) {
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(SkImageInfo::Make(10, 10, kRGBA_F16_SkColorType, kOpaque_SkAlphaType, cs));
|
|
|
|
bm.eraseColor(SK_ColorBLUE);
|
|
|
|
|
|
|
|
for (auto format : { SkEncodedImageFormat::kPNG,
|
|
|
|
SkEncodedImageFormat::kJPEG,
|
|
|
|
SkEncodedImageFormat::kWEBP }) {
|
|
|
|
auto data = SkEncodeBitmap(bm, format, 80);
|
|
|
|
auto gen = SkImageGeneratorNDK::MakeFromEncodedNDK(std::move(data));
|
|
|
|
if (!gen) {
|
|
|
|
ERRORF(r, "Failed to encode!");
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!cs) cs = SkColorSpace::MakeSRGB();
|
|
|
|
REPORTER_ASSERT(r, SkColorSpace::Equals(gen->getInfo().colorSpace(), cs.get()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_ColorSpace, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/CMYK.jpg",
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
for (sk_sp<SkColorSpace> cs : {
|
|
|
|
sk_sp<SkColorSpace>(nullptr),
|
|
|
|
SkColorSpace::MakeSRGB(),
|
|
|
|
SkColorSpace::MakeSRGBLinear(),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kRec2020, SkNamedGamut::kSRGB),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kRec2020, SkNamedGamut::kRec2020),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::kSRGB, SkNamedGamut::kDisplayP3),
|
|
|
|
SkColorSpace::MakeRGB(SkNamedTransferFn::k2Dot2, SkNamedGamut::kAdobeRGB),
|
|
|
|
SkColorSpace::MakeRGB(k2Dot6, kDCIP3),
|
|
|
|
}) {
|
|
|
|
auto info = gen->getInfo().makeColorSpace(cs);
|
|
|
|
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
|
|
|
|
std::vector<sk_sp<SkColorSpace>> unsupportedCs;
|
|
|
|
for (auto gamut : { SkNamedGamut::kSRGB, SkNamedGamut::kAdobeRGB, SkNamedGamut::kDisplayP3,
|
|
|
|
SkNamedGamut::kRec2020, SkNamedGamut::kXYZ }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::kPQ, gamut));
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::kHLG, gamut));
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(k2Dot6, gamut));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto gamut : { SkNamedGamut::kSRGB, SkNamedGamut::kDisplayP3,
|
|
|
|
SkNamedGamut::kRec2020, SkNamedGamut::kXYZ }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::k2Dot2, gamut));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto gamut : { SkNamedGamut::kAdobeRGB, SkNamedGamut::kDisplayP3,
|
|
|
|
SkNamedGamut::kXYZ }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::kRec2020, gamut));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto gamut : { SkNamedGamut::kAdobeRGB, SkNamedGamut::kDisplayP3,
|
|
|
|
SkNamedGamut::kRec2020, SkNamedGamut::kXYZ }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::kLinear, gamut));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto gamut : { SkNamedGamut::kAdobeRGB,
|
|
|
|
SkNamedGamut::kRec2020, SkNamedGamut::kXYZ }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(SkNamedTransferFn::kSRGB, gamut));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto fn : { SkNamedTransferFn::kSRGB, SkNamedTransferFn::k2Dot2,
|
|
|
|
SkNamedTransferFn::kLinear, SkNamedTransferFn::kRec2020 }) {
|
|
|
|
unsupportedCs.push_back(SkColorSpace::MakeRGB(fn, kDCIP3));
|
|
|
|
}
|
|
|
|
|
|
|
|
for (auto unsupported : unsupportedCs) {
|
|
|
|
auto info = gen->getInfo().makeColorSpace(unsupported);
|
|
|
|
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, !gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_reuseNoColorSpace, r) {
|
|
|
|
static const struct {
|
|
|
|
const char* fPath;
|
|
|
|
sk_sp<SkColorSpace> fCorrectedColorSpace;
|
|
|
|
bool fIsOpaque;
|
|
|
|
} recs[] = {
|
|
|
|
// AImageDecoder defaults to ADATASPACE_UNKNOWN for this image.
|
|
|
|
{"images/wide_gamut_yellow_224_224_64.jpeg", SkColorSpace::MakeSRGB(), true},
|
|
|
|
// This image is SRGB, so convert to a different color space.
|
|
|
|
{"images/example_1.png", SkColorSpace::MakeRGB(SkNamedTransferFn::k2Dot2,
|
|
|
|
SkNamedGamut::kAdobeRGB), false},
|
|
|
|
};
|
|
|
|
for (auto& rec : recs) {
|
|
|
|
auto gen = make_generator(rec.fPath, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
REPORTER_ASSERT(r, gen->getInfo().colorSpace()->isSRGB());
|
|
|
|
REPORTER_ASSERT(r, gen->getInfo().isOpaque() == rec.fIsOpaque);
|
|
|
|
|
|
|
|
auto noColorCorrection = gen->getInfo().makeColorSpace(nullptr);
|
|
|
|
if (rec.fIsOpaque) {
|
|
|
|
// Use something other than the default color type to verify that the modified color
|
|
|
|
// type is used even when the color space is reset.
|
|
|
|
noColorCorrection = noColorCorrection.makeColorType(kRGB_565_SkColorType);
|
|
|
|
}
|
|
|
|
|
|
|
|
SkBitmap orig;
|
|
|
|
orig.allocPixels(noColorCorrection);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(orig.pixmap()));
|
|
|
|
|
|
|
|
SkBitmap corrected;
|
|
|
|
corrected.allocPixels(noColorCorrection.makeColorSpace(rec.fCorrectedColorSpace));
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(corrected.pixmap()));
|
|
|
|
|
2020-08-05 20:51:10 +00:00
|
|
|
REPORTER_ASSERT(r, !ToolUtils::equal_pixels(orig, corrected));
|
2020-08-05 14:44:17 +00:00
|
|
|
|
|
|
|
SkBitmap reuse;
|
|
|
|
reuse.allocPixels(noColorCorrection);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(reuse.pixmap()));
|
|
|
|
|
2020-08-05 20:51:10 +00:00
|
|
|
REPORTER_ASSERT(r, ToolUtils::equal_pixels(orig, reuse));
|
2020-08-05 14:44:17 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// The NDK supports scaling up to arbitrary dimensions. Skia forces clients to do this in a
|
|
|
|
// separate step, so the client is in charge of how to do the upscale.
|
|
|
|
DEF_TEST(NdkDecode_noUpscale, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/CMYK.jpg",
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
const auto actualDimensions = gen->getInfo().dimensions();
|
|
|
|
const int width = actualDimensions.width();
|
|
|
|
const int height = actualDimensions.height();
|
|
|
|
for (SkISize dims : {
|
|
|
|
SkISize{width*2, height*2},
|
|
|
|
SkISize{width + 1, height + 1},
|
|
|
|
}) {
|
|
|
|
auto info = gen->getInfo().makeDimensions(dims);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, !gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// libwebp supports downscaling to an arbitrary scale factor, and this is supported by the NDK.
|
|
|
|
DEF_TEST(NdkDecode_webpArbitraryDownscale, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/yellow_rose.webp",
|
|
|
|
"images/webp-color-profile-lossless.webp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
const auto actualDimensions = gen->getInfo().dimensions();
|
|
|
|
const int width = actualDimensions.width();
|
|
|
|
const int height = actualDimensions.height();
|
|
|
|
for (SkISize dims : {
|
|
|
|
SkISize{width/2, height/2},
|
|
|
|
SkISize{width/4, height/4},
|
|
|
|
SkISize{width/7, height/7},
|
|
|
|
SkISize{width - 1, height - 1},
|
|
|
|
SkISize{1, 1},
|
|
|
|
SkISize{5, 20}
|
|
|
|
}) {
|
|
|
|
auto info = gen->getInfo().makeDimensions(dims);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
|
|
|
|
REPORTER_ASSERT(r, info.alphaType() != kUnpremul_SkAlphaType);
|
|
|
|
auto unpremulInfo = info.makeAlphaType(kUnpremul_SkAlphaType);
|
|
|
|
bm.allocPixels(unpremulInfo);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// libjpeg-turbo supports downscaling to some scale factors.
|
|
|
|
DEF_TEST(NdkDecode_jpegDownscale, r) {
|
|
|
|
static const struct {
|
|
|
|
const char* fPath;
|
|
|
|
SkISize fSupportedSizes[4];
|
|
|
|
} recs[] = {
|
|
|
|
{"images/CMYK.jpg", {{642,516},{321,258},{161,129},{81,65}}},
|
|
|
|
{"images/dog.jpg", {{180,180},{90,90},{45,45},{23,23}}},
|
|
|
|
{"images/grayscale.jpg", {{128,128},{64,64},{32,32},{16,16}}},
|
|
|
|
{"images/brickwork-texture.jpg", {{512,512},{256,256},{128,128},{64,64}}},
|
|
|
|
{"images/mandrill_h2v1.jpg", {{512,512},{256,256},{128,128},{64,64}}},
|
|
|
|
{"images/ducky.jpg", {{489,537},{245,269},{123,135},{62,68}}},
|
|
|
|
};
|
|
|
|
for (auto& rec : recs) {
|
|
|
|
auto gen = make_generator(rec.fPath, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
for (SkISize dims : rec.fSupportedSizes) {
|
|
|
|
auto info = gen->getInfo().makeDimensions(dims);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
if (!gen->getPixels(bm.pixmap())) {
|
|
|
|
ERRORF(r, "failed to decode %s to {%i,%i}\n", rec.fPath, dims.width(),
|
|
|
|
dims.height());
|
|
|
|
}
|
|
|
|
|
|
|
|
REPORTER_ASSERT(r, info.alphaType() != kUnpremul_SkAlphaType);
|
|
|
|
auto unpremulInfo = info.makeAlphaType(kUnpremul_SkAlphaType);
|
|
|
|
bm.allocPixels(unpremulInfo);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_reuseJpeg, r) {
|
|
|
|
auto gen = make_generator("images/CMYK.jpg", r);
|
|
|
|
if (!gen) return;
|
|
|
|
|
|
|
|
SkImageInfo info = gen->getInfo();
|
|
|
|
SkBitmap orig;
|
|
|
|
orig.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(orig.pixmap()));
|
|
|
|
|
|
|
|
info = info.makeWH(321, 258);
|
|
|
|
SkBitmap downscaled;
|
|
|
|
downscaled.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(downscaled.pixmap()));
|
|
|
|
|
|
|
|
SkBitmap reuse;
|
|
|
|
reuse.allocPixels(gen->getInfo());
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(reuse.pixmap()));
|
|
|
|
|
2020-08-05 20:51:10 +00:00
|
|
|
REPORTER_ASSERT(r, ToolUtils::equal_pixels(orig, reuse));
|
2020-08-05 14:44:17 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// The NDK supports scaling down to arbitrary dimensions. Skia forces clients to do this in a
|
|
|
|
// separate step, so the client is in charge of how to do the downscale.
|
|
|
|
DEF_TEST(NdkDecode_noDownscale, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
const auto actualDimensions = gen->getInfo().dimensions();
|
|
|
|
const int width = actualDimensions.width();
|
|
|
|
const int height = actualDimensions.height();
|
|
|
|
for (SkISize dims : {
|
|
|
|
SkISize{width/2, height/2},
|
|
|
|
SkISize{width/3, height/3},
|
|
|
|
SkISize{width/4, height/4},
|
|
|
|
SkISize{width/8, height/8},
|
|
|
|
SkISize{width - 1, height - 1},
|
|
|
|
}) {
|
|
|
|
auto info = gen->getInfo().makeDimensions(dims);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, !gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_Gray8, r) {
|
|
|
|
static const struct {
|
|
|
|
const char* fPath;
|
|
|
|
bool fGrayscale;
|
|
|
|
} recs[] = {
|
|
|
|
{"images/CMYK.jpg", false},
|
|
|
|
{"images/arrow.png", false},
|
|
|
|
{"images/baby_tux.webp", false},
|
|
|
|
{"images/color_wheel.gif", false},
|
|
|
|
{"images/rle.bmp", false},
|
|
|
|
{"images/color_wheel.ico", false},
|
|
|
|
{"images/google_chrome.ico", false},
|
|
|
|
{"images/mandrill.wbmp", true},
|
|
|
|
{"images/grayscale.jpg", true},
|
|
|
|
{"images/grayscale.png", true},
|
|
|
|
};
|
|
|
|
for (auto& rec : recs) {
|
|
|
|
auto gen = make_generator(rec.fPath, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
SkImageInfo info = gen->getInfo();
|
|
|
|
if (rec.fGrayscale) {
|
|
|
|
REPORTER_ASSERT(r, info.colorType() == kGray_8_SkColorType);
|
|
|
|
REPORTER_ASSERT(r, info.alphaType() == kOpaque_SkAlphaType);
|
|
|
|
} else {
|
|
|
|
info = info.makeColorType(kGray_8_SkColorType);
|
|
|
|
}
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
bool success = gen->getPixels(bm.pixmap());
|
|
|
|
if (success != rec.fGrayscale) {
|
|
|
|
ERRORF(r, "Expected decoding %s to Gray8 to %s. Actual: %s\n", rec.fPath,
|
|
|
|
(rec.fGrayscale ? "succeed" : "fail"), (success ? "succeed" : "fail"));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_Opaque_and_565, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/CMYK.jpg",
|
|
|
|
"images/dog.jpg",
|
|
|
|
"images/ducky.jpg",
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/example_1.png",
|
|
|
|
"images/explosion_sprites.png",
|
|
|
|
"images/lut_identity.png",
|
|
|
|
"images/grayscale.png",
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/yellow_rose.webp",
|
|
|
|
"images/webp-color-profile-lossless.webp",
|
|
|
|
"images/colorTables.gif",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/flightAnim.gif",
|
|
|
|
"images/randPixels.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
auto info = gen->getInfo().makeAlphaType(kOpaque_SkAlphaType);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
bool success = gen->getPixels(bm.pixmap());
|
|
|
|
REPORTER_ASSERT(r, success == gen->getInfo().isOpaque());
|
|
|
|
|
|
|
|
info = info.makeColorType(kRGB_565_SkColorType);
|
|
|
|
bm.allocPixels(info);
|
|
|
|
success = gen->getPixels(bm.pixmap());
|
|
|
|
REPORTER_ASSERT(r, success == gen->getInfo().isOpaque());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_AlwaysSupportedColorTypes, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/CMYK.jpg",
|
|
|
|
"images/dog.jpg",
|
|
|
|
"images/ducky.jpg",
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/example_1.png",
|
|
|
|
"images/explosion_sprites.png",
|
|
|
|
"images/lut_identity.png",
|
|
|
|
"images/grayscale.png",
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/yellow_rose.webp",
|
|
|
|
"images/webp-color-profile-lossless.webp",
|
|
|
|
"images/colorTables.gif",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/flightAnim.gif",
|
|
|
|
"images/randPixels.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
auto info = gen->getInfo().makeColorType(kRGBA_F16_SkColorType);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
|
|
|
|
// This also tests that we can reuse the same generator for a different
|
|
|
|
// color type.
|
|
|
|
info = info.makeColorType(kRGBA_8888_SkColorType);
|
|
|
|
bm.allocPixels(info);
|
|
|
|
REPORTER_ASSERT(r, gen->getPixels(bm.pixmap()));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
DEF_TEST(NdkDecode_UnsupportedColorTypes, r) {
|
|
|
|
for (const char* path: {
|
|
|
|
"images/CMYK.jpg",
|
|
|
|
"images/dog.jpg",
|
|
|
|
"images/ducky.jpg",
|
|
|
|
"images/arrow.png",
|
|
|
|
"images/example_1.png",
|
|
|
|
"images/explosion_sprites.png",
|
|
|
|
"images/lut_identity.png",
|
|
|
|
"images/grayscale.png",
|
|
|
|
"images/baby_tux.webp",
|
|
|
|
"images/yellow_rose.webp",
|
|
|
|
"images/webp-color-profile-lossless.webp",
|
|
|
|
"images/colorTables.gif",
|
|
|
|
"images/color_wheel.gif",
|
|
|
|
"images/flightAnim.gif",
|
|
|
|
"images/randPixels.gif",
|
|
|
|
"images/rle.bmp",
|
|
|
|
"images/color_wheel.ico",
|
|
|
|
"images/google_chrome.ico",
|
|
|
|
"images/mandrill.wbmp",
|
|
|
|
}) {
|
|
|
|
auto gen = make_generator(path, r);
|
|
|
|
if (!gen) continue;
|
|
|
|
|
|
|
|
for (SkColorType ct : {
|
|
|
|
kUnknown_SkColorType,
|
|
|
|
kAlpha_8_SkColorType,
|
|
|
|
kARGB_4444_SkColorType,
|
|
|
|
kRGB_888x_SkColorType,
|
|
|
|
kBGRA_8888_SkColorType,
|
|
|
|
kRGBA_1010102_SkColorType,
|
|
|
|
kBGRA_1010102_SkColorType,
|
|
|
|
kRGB_101010x_SkColorType,
|
|
|
|
kBGR_101010x_SkColorType,
|
|
|
|
kRGBA_F16Norm_SkColorType,
|
|
|
|
kRGBA_F32_SkColorType,
|
|
|
|
kR8G8_unorm_SkColorType,
|
|
|
|
kA16_float_SkColorType,
|
|
|
|
kR16G16_float_SkColorType,
|
|
|
|
kA16_unorm_SkColorType,
|
|
|
|
kR16G16_unorm_SkColorType,
|
|
|
|
kR16G16B16A16_unorm_SkColorType,
|
|
|
|
}) {
|
|
|
|
auto info = gen->getInfo().makeColorType(ct);
|
|
|
|
SkBitmap bm;
|
|
|
|
bm.allocPixels(info);
|
|
|
|
if (gen->getPixels(bm.pixmap())) {
|
|
|
|
ERRORF(r, "Expected decoding %s to %i to fail!", path, ct);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2020-08-05 20:51:10 +00:00
|
|
|
#endif // SK_ENABLE_NDK_IMAGES
|