summaryrefslogtreecommitdiffstats
path: root/base/gfx
diff options
context:
space:
mode:
authorglen@chromium.org <glen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-06 00:43:00 +0000
committerglen@chromium.org <glen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-06 00:43:00 +0000
commit596fe0c18f6bdcbb8a89adbdd53940927dfccbc3 (patch)
treee6ed6de2d16484bed2f29977edb631c41a422edc /base/gfx
parent71421c3fc725d9d55acba7a4233525f8b6e07350 (diff)
downloadchromium_src-596fe0c18f6bdcbb8a89adbdd53940927dfccbc3.zip
chromium_src-596fe0c18f6bdcbb8a89adbdd53940927dfccbc3.tar.gz
chromium_src-596fe0c18f6bdcbb8a89adbdd53940927dfccbc3.tar.bz2
Re-Retry. This is the change from hell.
Revert DCHECKs to what they used to be - turns out a bunch of stuff in the code depended on input.empty() == true. --- I believe the code (with your width() * bbp fix) is correct. The UMR errors occur when the source image contain alpha. I believe the issue comes from webkit glue image decoder, and the reason this only started triggering valgrind errors is that the old ones were masked by the change detailed in bug 12640 Also adds valgrind suppression for the new code. TBR=Nick BUG=12891,12640 TEST=none Review URL: http://codereview.chromium.org/119271 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@17811 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'base/gfx')
-rw-r--r--base/gfx/png_encoder.cc39
1 files changed, 34 insertions, 5 deletions
diff --git a/base/gfx/png_encoder.cc b/base/gfx/png_encoder.cc
index 5021721..f8b4bf0 100644
--- a/base/gfx/png_encoder.cc
+++ b/base/gfx/png_encoder.cc
@@ -5,6 +5,7 @@
#include "base/basictypes.h"
#include "base/gfx/png_encoder.h"
#include "base/logging.h"
+#include "base/scoped_ptr.h"
#include "third_party/skia/include/core/SkBitmap.h"
extern "C" {
@@ -197,9 +198,37 @@ bool PNGEncoder::Encode(const unsigned char* input, ColorFormat format,
bool PNGEncoder::EncodeBGRASkBitmap(const SkBitmap& input,
bool discard_transparency,
std::vector<unsigned char>* output) {
- SkAutoLockPixels input_lock(input);
- DCHECK(input.empty() || input.bytesPerPixel() == 4);
- return Encode(static_cast<unsigned char*>(input.getPixels()),
- PNGEncoder::FORMAT_BGRA, input.width(), input.height(),
- input.rowBytes(), discard_transparency, output);
+ static const int bbp = 4;
+
+ SkAutoLockPixels lock_input(input);
+ DCHECK(input.empty() || input.bytesPerPixel() == bbp);
+
+ // SkBitmaps are premultiplied, we need to unpremultiply them.
+ scoped_array<unsigned char> divided(
+ new unsigned char[input.width() * input.height() * bbp]);
+
+ int i = 0;
+ for (int y = 0; y < input.height(); y++) {
+ for (int x = 0; x < input.width(); x++) {
+ uint32 pixel = input.getAddr32(0, y)[x];
+
+ int alpha = SkColorGetA(pixel);
+ if (alpha != 0 && alpha != 255) {
+ divided[i + 0] = (SkColorGetR(pixel) << 8) / alpha;
+ divided[i + 1] = (SkColorGetG(pixel) << 8) / alpha;
+ divided[i + 2] = (SkColorGetB(pixel) << 8) / alpha;
+ divided[i + 3] = alpha;
+ } else {
+ divided[i + 0] = SkColorGetR(pixel);
+ divided[i + 1] = SkColorGetG(pixel);
+ divided[i + 2] = SkColorGetB(pixel);
+ divided[i + 3] = alpha;
+ }
+ i += bbp;
+ }
+ }
+
+ return Encode(divided.get(),
+ PNGEncoder::FORMAT_RGBA, input.width(), input.height(),
+ input.width() * bbp, discard_transparency, output);
}