aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/core/SkTemplates.h7
-rw-r--r--src/images/SkImageDecoder_libjpeg.cpp19
-rw-r--r--src/images/SkImageDecoder_libpng.cpp31
3 files changed, 44 insertions, 13 deletions
diff --git a/include/core/SkTemplates.h b/include/core/SkTemplates.h
index 27ebd41..d484389 100644
--- a/include/core/SkTemplates.h
+++ b/include/core/SkTemplates.h
@@ -61,8 +61,10 @@ private:
template <typename T> class SkAutoTDelete : SkNoncopyable {
public:
- SkAutoTDelete(T* obj) : fObj(obj) {}
- ~SkAutoTDelete() { delete fObj; }
+ SkAutoTDelete(T* obj, bool deleteWhenDone = true) : fObj(obj) {
+ this->deleteWhenDone = deleteWhenDone;
+ }
+ ~SkAutoTDelete() { if (deleteWhenDone) delete fObj; }
T* get() const { return fObj; }
void free() { delete fObj; fObj = NULL; }
@@ -70,6 +72,7 @@ public:
private:
T* fObj;
+ bool deleteWhenDone;
};
template <typename T> class SkAutoTDeleteArray : SkNoncopyable {
diff --git a/src/images/SkImageDecoder_libjpeg.cpp b/src/images/SkImageDecoder_libjpeg.cpp
index 358861e..514118d 100644
--- a/src/images/SkImageDecoder_libjpeg.cpp
+++ b/src/images/SkImageDecoder_libjpeg.cpp
@@ -328,8 +328,12 @@ bool SkJPEGImageDecoder::onDecode(SkStream* stream, SkBitmap* bm, Mode mode) {
bm->lockPixels();
JSAMPLE* rowptr = (JSAMPLE*)bm->getPixels();
bm->unlockPixels();
- bool reuseBitmap = (rowptr != NULL && (int) cinfo.output_width == bm->width() &&
- (int) cinfo.output_height == bm->height());
+ bool reuseBitmap = (rowptr != NULL);
+ if (reuseBitmap && ((int) cinfo.output_width != bm->width() ||
+ (int) cinfo.output_height != bm->height())) {
+ // Dimensions must match
+ return false;
+ }
if (!reuseBitmap) {
bm->setConfig(config, cinfo.output_width, cinfo.output_height);
@@ -389,9 +393,13 @@ bool SkJPEGImageDecoder::onDecode(SkStream* stream, SkBitmap* bm, Mode mode) {
bm->lockPixels();
JSAMPLE* rowptr = (JSAMPLE*)bm->getPixels();
- bool reuseBitmap = (rowptr != NULL && sampler.scaledWidth() == bm->width() &&
- sampler.scaledHeight() == bm->height());
+ bool reuseBitmap = (rowptr != NULL);
bm->unlockPixels();
+ if (reuseBitmap && (sampler.scaledWidth() != bm->width() ||
+ sampler.scaledHeight() != bm->height())) {
+ // Dimensions must match
+ return false;
+ }
if (!reuseBitmap) {
bm->setConfig(config, sampler.scaledWidth(), sampler.scaledHeight());
@@ -447,6 +455,9 @@ bool SkJPEGImageDecoder::onDecode(SkStream* stream, SkBitmap* bm, Mode mode) {
cinfo.output_height - cinfo.output_scanline)) {
return return_false(cinfo, *bm, "skip rows");
}
+ if (reuseBitmap) {
+ bm->notifyPixelsChanged();
+ }
jpeg_finish_decompress(&cinfo);
// SkDebugf("------------------- bm2 size %d [%d %d] %d\n", bm->getSize(), bm->width(), bm->height(), bm->config());
diff --git a/src/images/SkImageDecoder_libpng.cpp b/src/images/SkImageDecoder_libpng.cpp
index e550767..5cd86f7 100644
--- a/src/images/SkImageDecoder_libpng.cpp
+++ b/src/images/SkImageDecoder_libpng.cpp
@@ -291,8 +291,20 @@ bool SkPNGImageDecoder::onDecode(SkStream* sk_stream, SkBitmap* decodedBitmap,
const int sampleSize = this->getSampleSize();
SkScaledBitmapSampler sampler(origWidth, origHeight, sampleSize);
- decodedBitmap->setConfig(config, sampler.scaledWidth(),
- sampler.scaledHeight(), 0);
+ decodedBitmap->lockPixels();
+ void* rowptr = (void*) decodedBitmap->getPixels();
+ bool reuseBitmap = (rowptr != NULL);
+ decodedBitmap->unlockPixels();
+ if (reuseBitmap && (sampler.scaledWidth() != decodedBitmap->width() ||
+ sampler.scaledHeight() != decodedBitmap->height())) {
+ // Dimensions must match
+ return false;
+ }
+
+ if (!reuseBitmap) {
+ decodedBitmap->setConfig(config, sampler.scaledWidth(),
+ sampler.scaledHeight(), 0);
+ }
if (SkImageDecoder::kDecodeBounds_Mode == mode) {
return true;
}
@@ -312,10 +324,12 @@ bool SkPNGImageDecoder::onDecode(SkStream* sk_stream, SkBitmap* decodedBitmap,
SkAutoUnref aur(colorTable);
- if (!this->allocPixelRef(decodedBitmap,
- SkBitmap::kIndex8_Config == config ?
- colorTable : NULL)) {
- return false;
+ if (!reuseBitmap) {
+ if (!this->allocPixelRef(decodedBitmap,
+ SkBitmap::kIndex8_Config == config ?
+ colorTable : NULL)) {
+ return false;
+ }
}
SkAutoLockPixels alp(*decodedBitmap);
@@ -416,6 +430,9 @@ bool SkPNGImageDecoder::onDecode(SkStream* sk_stream, SkBitmap* decodedBitmap,
reallyHasAlpha |= substituteTranspColor(decodedBitmap, theTranspColor);
}
decodedBitmap->setIsOpaque(!reallyHasAlpha);
+ if (reuseBitmap) {
+ decodedBitmap->notifyPixelsChanged();
+ }
return true;
}
@@ -684,7 +701,7 @@ bool SkPNGImageDecoder::onDecodeRegion(SkBitmap* bm, SkIRect rect) {
png_ptr->pass = 0;
png_read_update_info(png_ptr, info_ptr);
- SkDebugf("Request size %d %d\n", requestedWidth, requestedHeight);
+ // SkDebugf("Request size %d %d\n", requestedWidth, requestedHeight);
int actualTop = rect.fTop;