/*
* Copyright 2016 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#ifndef SkBitmapKey_DEFINED
#define SkBitmapKey_DEFINED
#include "SkBitmap.h"
#include "SkImage.h"
#include "SkCanvas.h"
struct SkBitmapKey {
SkIRect fSubset;
uint32_t fID;
bool operator==(const SkBitmapKey& rhs) const {
return fID == rhs.fID && fSubset == rhs.fSubset;
}
bool operator!=(const SkBitmapKey& rhs) const { return !(*this == rhs); }
};
/**
This class has all the advantages of SkBitmaps and SkImages.
*/
class SkImageSubset {
public:
SkImageSubset(sk_sp<SkImage> i, SkIRect subset = {0, 0, 0, 0})
: fImage(std::move(i)) {
if (!fImage) {
fSubset = {0, 0, 0, 0};
fID = 0;
return;
}
fID = fImage->uniqueID();
if (subset.isEmpty()) {
fSubset = fImage->bounds();
// SkImage always has a non-zero dimensions.
SkASSERT(!fSubset.isEmpty());
} else {
fSubset = subset;
if (!fSubset.intersect(fImage->bounds())) {
fImage = nullptr;
fSubset = {0, 0, 0, 0};
fID = 0;
}
}
}
void setID(uint32_t id) { fID = id; }
bool isValid() const { return fImage != nullptr; }
SkIRect bounds() const { return SkIRect::MakeSize(this->dimensions()); }
SkISize dimensions() const { return fSubset.size(); }
sk_sp<SkImage> makeImage() const {
return fSubset == fImage->bounds() ? fImage : fImage->makeSubset(fSubset);
}
SkBitmapKey getKey() const { return SkBitmapKey{fSubset, fID}; }
void draw(SkCanvas* canvas, SkPaint* paint) const {
SkASSERT(this->isValid());
SkRect src = SkRect::Make(fSubset),
dst = SkRect::Make(this->bounds());
canvas->drawImageRect(fImage.get(), src, dst, paint);
}
private:
SkIRect fSubset;
sk_sp<SkImage> fImage;
uint32_t fID;
};
#endif // SkBitmapKey_DEFINED