Home | History | Annotate | Download | only in gm
      1 /*
      2  * Copyright 2017 Google Inc.
      3  *
      4  * Use of this source code is governed by a BSD-style license that can be
      5  * found in the LICENSE file.
      6  */
      7 
      8 #include "gm.h"
      9 #include "SkImage.h"
     10 #include "SkJpegEncoder.h"
     11 
     12 #include "Resources.h"
     13 
     14 namespace skiagm {
     15 
     16 static inline void read_into_pixmap(SkPixmap* dst, SkImageInfo dstInfo, void* dstPixels,
     17         sk_sp<SkImage> src) {
     18     dst->reset(dstInfo, dstPixels, dstInfo.minRowBytes());
     19     src->readPixels(*dst, 0, 0, SkImage::CachingHint::kDisallow_CachingHint);
     20 }
     21 
     22 static inline sk_sp<SkImage> encode_pixmap_and_make_image(const SkPixmap& src,
     23         SkJpegEncoder::AlphaOption alphaOption, SkTransferFunctionBehavior blendBehavior) {
     24     SkDynamicMemoryWStream dst;
     25     SkJpegEncoder::Options options;
     26     options.fAlphaOption = alphaOption;
     27     options.fBlendBehavior = blendBehavior;
     28     SkJpegEncoder::Encode(&dst, src, options);
     29     return SkImage::MakeFromEncoded(dst.detachAsData());
     30 }
     31 
     32 class EncodeJpegAlphaOptsGM : public GM {
     33 public:
     34     EncodeJpegAlphaOptsGM() {}
     35 
     36 protected:
     37     SkString onShortName() override {
     38         return SkString("encode-alpha-jpeg");
     39     }
     40 
     41     SkISize onISize() override {
     42         return SkISize::Make(400, 200);
     43     }
     44 
     45     void onDraw(SkCanvas* canvas) override {
     46         sk_sp<SkImage> srcImg = GetResourceAsImage("images/rainbow-gradient.png");
     47         fStorage.reset(srcImg->width() * srcImg->height() *
     48                 SkColorTypeBytesPerPixel(kRGBA_F16_SkColorType));
     49 
     50         SkPixmap src;
     51         SkImageInfo info = SkImageInfo::MakeN32Premul(srcImg->width(), srcImg->height(),
     52                 canvas->imageInfo().colorSpace() ? SkColorSpace::MakeSRGB() : nullptr);
     53         read_into_pixmap(&src, info, fStorage.get(), srcImg);
     54 
     55         SkTransferFunctionBehavior behavior = canvas->imageInfo().colorSpace() ?
     56                 SkTransferFunctionBehavior::kRespect : SkTransferFunctionBehavior::kIgnore;
     57 
     58         // Encode 8888 premul.
     59         sk_sp<SkImage> img0 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kIgnore,
     60                 behavior);
     61         sk_sp<SkImage> img1 = encode_pixmap_and_make_image(src,
     62                 SkJpegEncoder::AlphaOption::kBlendOnBlack, behavior);
     63         canvas->drawImage(img0, 0.0f, 0.0f);
     64         canvas->drawImage(img1, 0.0f, 100.0f);
     65 
     66         // Encode 8888 unpremul
     67         info = info.makeAlphaType(kUnpremul_SkAlphaType);
     68         read_into_pixmap(&src, info, fStorage.get(), srcImg);
     69         img0 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kIgnore, behavior);
     70         img1 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kBlendOnBlack,
     71                 behavior);
     72         canvas->drawImage(img0, 100.0f, 0.0f);
     73         canvas->drawImage(img1, 100.0f, 100.0f);
     74 
     75         if (canvas->imageInfo().colorSpace()) {
     76             // Encode F16 premul
     77             info = SkImageInfo::Make(srcImg->width(), srcImg->height(), kRGBA_F16_SkColorType,
     78                     kPremul_SkAlphaType, SkColorSpace::MakeSRGBLinear());
     79             read_into_pixmap(&src, info, fStorage.get(), srcImg);
     80             img0 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kIgnore, behavior);
     81             img1 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kBlendOnBlack,
     82                     behavior);
     83             canvas->drawImage(img0, 200.0f, 0.0f);
     84             canvas->drawImage(img1, 200.0f, 100.0f);
     85 
     86             // Encode F16 unpremul
     87             info = info.makeAlphaType(kUnpremul_SkAlphaType);
     88             read_into_pixmap(&src, info, fStorage.get(), srcImg);
     89             img0 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kIgnore, behavior);
     90             img1 = encode_pixmap_and_make_image(src, SkJpegEncoder::AlphaOption::kBlendOnBlack,
     91                     behavior);
     92             canvas->drawImage(img0, 300.0f, 0.0f);
     93             canvas->drawImage(img1, 300.0f, 100.0f);
     94         }
     95     }
     96 
     97 private:
     98     SkAutoTMalloc<uint8_t> fStorage;
     99 
    100     typedef GM INHERITED;
    101 };
    102 
    103 DEF_GM( return new EncodeJpegAlphaOptsGM; )
    104 
    105 };
    106