SkImage_Generator.cpp revision 61624f0c716b576706659750d87b6956f4c15722
1/*
2 * Copyright 2015 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 "SkImage_Base.h"
9#include "SkBitmap.h"
10#include "SkData.h"
11#include "SkImageCacherator.h"
12#include "SkImagePriv.h"
13#include "SkPixelRef.h"
14
15class SkImage_Generator : public SkImage_Base {
16public:
17    SkImage_Generator(SkImageCacherator::Validator* validator)
18        : INHERITED(validator->fInfo.width(), validator->fInfo.height(), validator->fUniqueID)
19        , fCache(validator)
20    {}
21
22    virtual SkImageInfo onImageInfo() const override {
23        return fCache.info();
24    }
25    SkAlphaType onAlphaType() const override {
26        return fCache.info().alphaType();
27    }
28
29    bool onReadPixels(const SkImageInfo&, void*, size_t, int srcX, int srcY, CachingHint) const override;
30    SkImageCacherator* peekCacherator() const override { return &fCache; }
31    SkData* onRefEncoded(GrContext*) const override;
32    sk_sp<SkImage> onMakeSubset(const SkIRect&) const override;
33    bool getROPixels(SkBitmap*, SkColorSpace* dstColorSpace, CachingHint) const override;
34    GrTexture* asTextureRef(GrContext*, const GrSamplerParams&, SkColorSpace*,
35                            sk_sp<SkColorSpace>*) const override;
36    bool onIsLazyGenerated() const override { return true; }
37
38private:
39    mutable SkImageCacherator fCache;
40
41    typedef SkImage_Base INHERITED;
42};
43
44///////////////////////////////////////////////////////////////////////////////
45
46bool SkImage_Generator::onReadPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRB,
47                                     int srcX, int srcY, CachingHint chint) const {
48    SkColorSpace* dstColorSpace = dstInfo.colorSpace();
49    SkBitmap bm;
50    if (kDisallow_CachingHint == chint) {
51        SkImageCacherator::CachedFormat cacheFormat = fCache.chooseCacheFormat(dstColorSpace);
52        if (fCache.lockAsBitmapOnlyIfAlreadyCached(&bm, cacheFormat)) {
53            return bm.readPixels(dstInfo, dstPixels, dstRB, srcX, srcY);
54        } else {
55            // Try passing the caller's buffer directly down to the generator. If this fails we
56            // may still succeed in the general case, as the generator may prefer some other
57            // config, which we could then convert via SkBitmap::readPixels.
58            if (fCache.directGeneratePixels(dstInfo, dstPixels, dstRB, srcX, srcY)) {
59                return true;
60            }
61            // else fall through
62        }
63    }
64
65    if (this->getROPixels(&bm, dstColorSpace, chint)) {
66        return bm.readPixels(dstInfo, dstPixels, dstRB, srcX, srcY);
67    }
68    return false;
69}
70
71SkData* SkImage_Generator::onRefEncoded(GrContext* ctx) const {
72    return fCache.refEncoded(ctx);
73}
74
75bool SkImage_Generator::getROPixels(SkBitmap* bitmap, SkColorSpace* dstColorSpace,
76                                    CachingHint chint) const {
77    return fCache.lockAsBitmap(bitmap, this, dstColorSpace, chint);
78}
79
80GrTexture* SkImage_Generator::asTextureRef(GrContext* ctx, const GrSamplerParams& params,
81                                           SkColorSpace* dstColorSpace,
82                                           sk_sp<SkColorSpace>* texColorSpace) const {
83    return fCache.lockAsTexture(ctx, params, dstColorSpace, texColorSpace, this);
84}
85
86sk_sp<SkImage> SkImage_Generator::onMakeSubset(const SkIRect& subset) const {
87    SkASSERT(fCache.info().bounds().contains(subset));
88    SkASSERT(fCache.info().bounds() != subset);
89
90    const SkIRect generatorSubset = subset.makeOffset(fCache.fOrigin.x(), fCache.fOrigin.y());
91    SkImageCacherator::Validator validator(fCache.fSharedGenerator, &generatorSubset);
92    return validator ? sk_sp<SkImage>(new SkImage_Generator(&validator)) : nullptr;
93}
94
95sk_sp<SkImage> SkImage::MakeFromGenerator(SkImageGenerator* generator, const SkIRect* subset) {
96    SkImageCacherator::Validator validator(SkImageCacherator::SharedGenerator::Make(generator),
97                                           subset);
98
99    return validator ? sk_make_sp<SkImage_Generator>(&validator) : nullptr;
100}
101