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 #ifndef SkImageFilterCache_DEFINED 9 #define SkImageFilterCache_DEFINED 10 11 #include "include/core/SkMatrix.h" 12 #include "include/core/SkRect.h" 13 #include "include/core/SkRefCnt.h" 14 #include "include/private/base/SkAssert.h" 15 #include "include/private/base/SkDebug.h" 16 17 #include <cstddef> 18 #include <cstdint> 19 20 class SkImageFilter; 21 namespace skif { class FilterResult; } 22 23 struct SkImageFilterCacheKey { SkImageFilterCacheKeySkImageFilterCacheKey24 SkImageFilterCacheKey(const uint32_t uniqueID, const SkMatrix& matrix, 25 const SkIRect& clipBounds, uint32_t srcGenID, const SkIRect& srcSubset) 26 : fUniqueID(uniqueID) 27 , fMatrix(matrix) 28 , fClipBounds(clipBounds) 29 , fSrcGenID(srcGenID) 30 , fSrcSubset(srcSubset) { 31 // Assert that Key is tightly-packed, since it is hashed. 32 static_assert(sizeof(SkImageFilterCacheKey) == sizeof(uint32_t) + sizeof(SkMatrix) + 33 sizeof(SkIRect) + sizeof(uint32_t) + 4 * sizeof(int32_t), 34 "image_filter_key_tight_packing"); 35 fMatrix.getType(); // force initialization of type, so hashes match 36 SkASSERT(fMatrix.isFinite()); // otherwise we can't rely on == self when comparing keys 37 } 38 39 uint32_t fUniqueID; 40 SkMatrix fMatrix; 41 SkIRect fClipBounds; 42 uint32_t fSrcGenID; 43 SkIRect fSrcSubset; 44 45 bool operator==(const SkImageFilterCacheKey& other) const { 46 return fUniqueID == other.fUniqueID && 47 fMatrix == other.fMatrix && 48 fClipBounds == other.fClipBounds && 49 fSrcGenID == other.fSrcGenID && 50 fSrcSubset == other.fSrcSubset; 51 } 52 }; 53 54 // This cache maps from (filter's unique ID + CTM + clipBounds + src bitmap generation ID) to result 55 // NOTE: this is the _specific_ unique ID of the image filter, so refiltering the same image with a 56 // copy of the image filter (with exactly the same parameters) will not yield a cache hit. 57 class SkImageFilterCache : public SkRefCnt { 58 public: 59 static constexpr size_t kDefaultTransientSize = 32 * 1024 * 1024; 60 ~SkImageFilterCache()61 ~SkImageFilterCache() override {} 62 static sk_sp<SkImageFilterCache> Create(size_t maxBytes); 63 64 // Whether to create the cache if it doesn't yet exist. 65 enum class CreateIfNecessary : bool { kNo, kYes }; 66 static sk_sp<SkImageFilterCache> Get(CreateIfNecessary = CreateIfNecessary::kYes); 67 68 // Returns true on cache hit and updates 'result' to be the cached result. Returns false when 69 // not in the cache, in which case 'result' is not modified. 70 virtual bool get(const SkImageFilterCacheKey& key, 71 skif::FilterResult* result) const = 0; 72 // 'filter' is included in the caching to allow the purging of all of an image filter's cached 73 // results when it is destroyed. 74 virtual void set(const SkImageFilterCacheKey& key, const SkImageFilter* filter, 75 const skif::FilterResult& result) = 0; 76 virtual void purge() = 0; 77 virtual void purgeByImageFilter(const SkImageFilter*) = 0; 78 SkDEBUGCODE(virtual int count() const = 0;) 79 }; 80 81 #endif 82