Index: src/core/SkPictureRecord.cpp |
diff --git a/src/core/SkPictureRecord.cpp b/src/core/SkPictureRecord.cpp |
index af1b8ffbc2134d0aa937c49429f61163e550d806..001276b5c276b8c58875e3b2ef68cde54e53735b 100644 |
--- a/src/core/SkPictureRecord.cpp |
+++ b/src/core/SkPictureRecord.cpp |
@@ -900,17 +900,40 @@ SkSurface* SkPictureRecord::onNewSurface(const SkImageInfo& info, const SkSurfac |
return NULL; |
} |
-int SkPictureRecord::addBitmap(const SkBitmap& bitmap) { |
+static bool equivalent(const SkBitmap& a, const SkBitmap& b) { |
+ if (a.info() != b.info() || a.pixelRefOrigin() != b.pixelRefOrigin()) { |
+ return false; |
reed1
2014/11/12 20:00:55
wonder if we should just compare width/height inst
|
+ } |
+ if (a.pixelRef() == b.pixelRef()) { |
+ return true; |
+ } |
+ SkAutoLockPixels al(a), bl(b); |
reed1
2014/11/12 20:00:56
1. what if a or b is backed by a texture?
2. what
|
+ SkASSERT(a.getSize() == b.getSize()); |
reed1
2014/11/12 20:00:55
a and b can have diff rowbytes, but be "logically"
|
+ return 0 == memcmp(a.getPixels(), b.getPixels(), a.getSize()); |
reed1
2014/11/12 20:00:55
per-scanline is the safe way, given a.rowbytes may
|
+} |
+ |
+void SkPictureRecord::addBitmap(const SkBitmap& bitmap) { |
+ // First see if we already have this bitmap. This deduplication should really |
+ // only be important for our tests, where bitmaps tend not to be tagged immutable. |
+ // In Chrome (and hopefully Android?) they're typically immutable. |
+ for (int i = 0; i < fBitmaps.count(); i++) { |
+ if (equivalent(fBitmaps[i], bitmap)) { |
+ this->addInt(i); // Unlike the rest, bitmap indices are 0-based. |
+ return; |
+ } |
+ } |
+ // Don't have it. We'll add it to our list, making sure it's tagged as immutable. |
if (bitmap.isImmutable()) { |
+ // Shallow copies of bitmaps are cheap, so immutable == fast. |
fBitmaps.push_back(bitmap); |
} else { |
+ // If you see this block on a memory profile, it's a good opportunity to reduce RAM usage. |
SkBitmap copy; |
bitmap.copyTo(©); |
copy.setImmutable(); |
fBitmaps.push_back(copy); |
} |
- this->addInt(fBitmaps.count()-1); // Unlike the rest, bitmap indicies are 0-based. |
- return fBitmaps.count(); |
+ this->addInt(fBitmaps.count()-1); // Remember, 0-based. |
} |
void SkPictureRecord::addMatrix(const SkMatrix& matrix) { |