• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2016 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 "bench/Benchmark.h"
9 #include "include/core/SkCanvas.h"
10 #include "include/core/SkColorSpace.h"
11 #include "include/core/SkImage.h"
12 #include "include/core/SkPaint.h"
13 #include "include/core/SkSurface.h"
14 
15 class GrMipMapBench: public Benchmark {
16     sk_sp<SkSurface> fSurface;
17     SkString fName;
18     const int fW, fH;
19 
20 public:
GrMipMapBench(int w,int h)21     GrMipMapBench(int w, int h) : fW(w), fH(h) {
22         fName.printf("gr_mipmap_build_%dx%d", w, h);
23     }
24 
25 protected:
isSuitableFor(Backend backend)26     bool isSuitableFor(Backend backend) override {
27         return kGPU_Backend == backend;
28     }
29 
onGetName()30     const char* onGetName() override { return fName.c_str(); }
31 
onDraw(int loops,SkCanvas * canvas)32     void onDraw(int loops, SkCanvas* canvas) override {
33         if (!fSurface) {
34             auto context = canvas->recordingContext();
35             if (!context) {
36                 return;
37             }
38             auto srgb = SkColorSpace::MakeSRGB();
39             SkImageInfo info =
40                     SkImageInfo::Make(fW, fH, kRGBA_8888_SkColorType, kPremul_SkAlphaType, srgb);
41             // We're benching the regeneration of the mip levels not the need to allocate them every
42             // frame. Thus we create the surface with mips to begin with.
43             fSurface = SkSurface::MakeRenderTarget(context,
44                                                    skgpu::Budgeted::kNo,
45                                                    info,
46                                                    0,
47                                                    kBottomLeft_GrSurfaceOrigin,
48                                                    nullptr,
49                                                    true);
50         }
51 
52         // Clear surface once:
53         fSurface->getCanvas()->clear(SK_ColorBLACK);
54 
55         SkSamplingOptions sampling(SkFilterMode::kLinear,
56                                    SkMipmapMode::kLinear);
57         SkPaint paint;
58         paint.setColor(SK_ColorWHITE);
59         for (int i = 0; i < loops; i++) {
60             // Touch surface so mips are dirtied
61             fSurface->getCanvas()->drawPoint(0, 0, paint);
62 
63             // Draw reduced version of surface to original canvas, to trigger mip generation
64             canvas->save();
65             canvas->scale(0.1f, 0.1f);
66             canvas->drawImage(fSurface->makeImageSnapshot(), 0, 0, sampling, &paint);
67             canvas->restore();
68         }
69     }
70 
onPerCanvasPostDraw(SkCanvas *)71     void onPerCanvasPostDraw(SkCanvas*) override {
72         fSurface.reset(nullptr);
73     }
74 
75 private:
76     using INHERITED = Benchmark;
77 };
78 
79 // Build variants that exercise the width and heights being even or odd at each level, as the
80 // impl specializes on each of these.
81 //
82 DEF_BENCH( return new GrMipMapBench(511, 511); )
83 DEF_BENCH( return new GrMipMapBench(512, 511); )
84 DEF_BENCH( return new GrMipMapBench(511, 512); )
85 DEF_BENCH( return new GrMipMapBench(512, 512); )
86