aboutsummaryrefslogtreecommitdiffhomepage
path: root/gm/deferredtextureimage.cpp
blob: 82dd90aa5fde59e332eb86dfab0c89e825dbce74 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
/*
 * Copyright 2016 Google Inc.
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */
#include <vector>

#include "gm.h"
#include "GrContext.h"
#include "SkMipMap.h"
#include "Resources.h"

#if SK_SUPPORT_GPU

class DeferredTextureImage_Medium : public skiagm::GM {
protected:
    SkString onShortName() override {
        return SkString("deferredtextureimage_medium");
    }

    SkISize onISize() override {
        return SkISize::Make(512 + 512 + 30, 1110);
    }

    void onDraw(SkCanvas* canvas) override {
        GrContext* context = canvas->getGrContext();
        if (!context) {
            skiagm::GM::DrawGpuOnlyMessage(canvas);
            return;
        }

        SkPaint paint;
        paint.setFilterQuality(kMedium_SkFilterQuality);

        int mipLevelCount = SkMipMap::ComputeLevelCount(512, 512);

        // create the deferred texture image
        SkImage::DeferredTextureImageUsageParams params[1];
        // These should cause mipmaps to be generated
        params[0].fMatrix = SkMatrix::MakeScale(0.25f, 0.25f);
        params[0].fQuality = kMedium_SkFilterQuality;
        size_t requiredMemoryInBytes = fDecodedImage->getDeferredTextureImageData(
            *context->threadSafeProxy(), params, 1, nullptr, SkSourceGammaTreatment::kRespect);
        if (requiredMemoryInBytes == 0) {
            SkDebugf("\nCould not create DeferredTextureImageData.\n");
            return;
        }

        std::vector<uint8_t> memory;
        memory.resize(requiredMemoryInBytes);
        fDecodedImage->getDeferredTextureImageData(
            *context->threadSafeProxy(), params, 1, memory.data(),
            SkSourceGammaTreatment::kRespect);
        sk_sp<SkImage> uploadedImage = SkImage::MakeFromDeferredTextureImageData(
            context, memory.data(), SkBudgeted::kNo);

        // draw a column using deferred texture images
        SkScalar offsetHeight = 10.f;
        // handle base mipmap level
        canvas->save();
        canvas->translate(10.f, offsetHeight);
        canvas->drawImage(uploadedImage, 0, 0, &paint);
        canvas->restore();
        offsetHeight += 512 + 10;
        // handle generated mipmap levels
        for (int i = 0; i < mipLevelCount; i++) {
            SkISize mipSize = SkMipMap::ComputeLevelSize(512, 512, i);
            canvas->save();
            canvas->translate(10.f, offsetHeight);
            canvas->scale(mipSize.width() / 512.f, mipSize.height() / 512.f);
            canvas->drawImage(uploadedImage, 0, 0, &paint);
            canvas->restore();
            offsetHeight += mipSize.height() + 10;
        }

        // draw a column using SkImage
        offsetHeight = 10;
        // handle base mipmap level
        canvas->save();
        canvas->translate(512.f + 20.f, offsetHeight);
        canvas->drawImage(fDecodedImage, 0, 0, &paint);
        canvas->restore();
        offsetHeight += 512 + 10;
        // handle generated mipmap levels
        for (int i = 0; i < mipLevelCount; i++) {
            SkISize mipSize = SkMipMap::ComputeLevelSize(512, 512, i);
            canvas->save();
            canvas->translate(512.f + 20.f, offsetHeight);
            canvas->scale(mipSize.width() / 512.f, mipSize.height() / 512.f);
            canvas->drawImage(fDecodedImage, 0, 0, &paint);
            canvas->restore();
            offsetHeight += mipSize.height() + 10;
        }
    }

private:

    void onOnceBeforeDraw() override {
        SkBitmap bitmap;
        if (!GetResourceAsBitmap("mandrill_512.png", &bitmap)) {
            bitmap.allocN32Pixels(1, 1);
            bitmap.eraseARGB(255, 255, 0, 0); // red == bad
        }
        fDecodedImage = SkImage::MakeFromBitmap(bitmap);
    }

    sk_sp<SkImage> fDecodedImage;

    typedef skiagm::GM INHERITED;
};

//////////////////////////////////////////////////////////////////////////////

DEF_GM( return new DeferredTextureImage_Medium; )

#endif