Index: gm/image.cpp |
diff --git a/gm/image.cpp b/gm/image.cpp |
index 991b4014f02aa3bfff0a2a3126a29f5210a21591..accdbd1670d099d89be0bc135ea8b8d28933be87 100644 |
--- a/gm/image.cpp |
+++ b/gm/image.cpp |
@@ -300,3 +300,122 @@ private: |
typedef skiagm::GM INHERITED; |
}; |
DEF_GM( return new ScalePixelsGM; ) |
+ |
+/////////////////////////////////////////////////////////////////////////////////////////////////// |
+ |
+#include "SkImageGenerator.h" |
+ |
+static SkImageInfo make_info(SkImage* img) { |
+ return SkImageInfo::MakeN32Premul(img->width(), img->height()); |
+} |
+ |
+class ImageGeneratorFromImage : public SkImageGenerator { |
+public: |
+ ImageGeneratorFromImage(SkImage* img) : INHERITED(make_info(img)), fImg(SkRef(img)) {} |
+ |
+protected: |
+ bool onGetPixels(const SkImageInfo& info, void* pixels, size_t rowBytes, SkPMColor ctable[], |
+ int* ctableCount) override { |
+ SkBitmap bm; |
+ bm.installPixels(info, pixels, rowBytes); |
+ bm.eraseColor(0); |
+ SkCanvas canvas(bm); |
+ canvas.drawImage(fImg, 0, 0, nullptr); |
+ return true; |
+ } |
+ |
+private: |
+ SkAutoTUnref<SkImage> fImg; |
+ |
+ typedef SkImageGenerator INHERITED; |
+}; |
+ |
+static SkImageGenerator* gen_raster(const SkImageInfo& info, GrContext*) { |
+ SkAutoTUnref<SkSurface> surface(SkSurface::NewRaster(info)); |
+ draw_contents(surface->getCanvas()); |
+ SkAutoTUnref<SkImage> img(surface->newImageSnapshot()); |
+ return new ImageGeneratorFromImage(img); |
+} |
+ |
+static SkImageGenerator* gen_picture(const SkImageInfo& info, GrContext*) { |
+ SkPictureRecorder recorder; |
+ draw_contents(recorder.beginRecording(SkRect::MakeIWH(info.width(), info.height()))); |
+ SkAutoTUnref<SkPicture> pict(recorder.endRecording()); |
+ return SkImageGenerator::NewFromPicture(info.dimensions(), pict, nullptr, nullptr); |
+} |
+ |
+static SkImageGenerator* gen_png(const SkImageInfo& info, GrContext*) { |
+ SkAutoTUnref<SkImage> image(make_raster(info, nullptr)); |
+ SkAutoTUnref<SkData> data(image->encode(SkImageEncoder::kPNG_Type, 100)); |
+ return SkImageGenerator::NewFromEncoded(data); |
+} |
+ |
+static SkImageGenerator* gen_jpg(const SkImageInfo& info, GrContext*) { |
+ SkAutoTUnref<SkImage> image(make_raster(info, nullptr)); |
+ SkAutoTUnref<SkData> data(image->encode(SkImageEncoder::kJPEG_Type, 100)); |
+ return SkImageGenerator::NewFromEncoded(data); |
+} |
+ |
+typedef SkImageGenerator* (*GeneratorMakerProc)(const SkImageInfo&, GrContext*); |
+ |
+static void show_scaled_generator(SkCanvas* canvas, SkImageGenerator* gen) { |
+ const SkImageInfo genInfo = gen->getInfo(); |
+ |
+ SkAutoCanvasRestore acr(canvas, true); |
+ |
+ SkBitmap bm; |
+ bm.allocPixels(genInfo); |
+ if (gen->getPixels(bm.info(), bm.getPixels(), bm.rowBytes())) { |
+ canvas->drawBitmap(bm, 0, 0, nullptr); |
+ } |
+ canvas->translate(110, 0); |
+ |
+ const float scales[] = { 0.75f, 0.5f, 0.25f }; |
+ for (auto scale : scales) { |
+ SkImageGenerator::SupportedSizes sizes; |
+ if (gen->computeScaledDimensions(scale, &sizes)) { |
+ const SkImageInfo info = SkImageInfo::MakeN32Premul(sizes.fSizes[0].width(), |
+ sizes.fSizes[0].height()); |
+ bm.allocPixels(info); |
+ SkPixmap pmap; |
+ bm.peekPixels(&pmap); |
+ if (gen->generateScaledPixels(pmap)) { |
+ canvas->drawBitmap(bm, 0, (genInfo.height() - info.height())/2, nullptr); |
+ } |
+ } |
+ canvas->translate(100, 0); |
+ } |
+} |
+ |
+class ScaleGeneratorGM : public skiagm::GM { |
+public: |
+ ScaleGeneratorGM() {} |
+ |
+protected: |
+ SkString onShortName() override { |
+ return SkString("scale-generator"); |
+ } |
+ |
+ SkISize onISize() override { |
+ return SkISize::Make(960, 1200); |
+ } |
+ |
+ void onDraw(SkCanvas* canvas) override { |
+ const SkImageInfo info = SkImageInfo::MakeN32Premul(100, 100); |
+ |
+ const GeneratorMakerProc procs[] = { |
+ gen_raster, gen_picture, gen_png, gen_jpg, |
+ }; |
+ for (auto& proc : procs) { |
+ SkAutoTDelete<SkImageGenerator> gen(proc(info, canvas->getGrContext())); |
+ if (gen) { |
+ show_scaled_generator(canvas, gen); |
+ } |
+ canvas->translate(0, 120); |
+ } |
+ } |
+ |
+private: |
+ typedef skiagm::GM INHERITED; |
+}; |
+DEF_GM( return new ScaleGeneratorGM; ) |