| OLD | NEW |
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "base/gfx/jpeg_codec.h" | 5 #include "base/gfx/jpeg_codec.h" |
| 6 | 6 |
| 7 #include <setjmp.h> | 7 #include <setjmp.h> |
| 8 | 8 |
| 9 #include "base/logging.h" | 9 #include "base/logging.h" |
| 10 #include "base/scoped_ptr.h" | 10 #include "base/scoped_ptr.h" |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 177 jpeg_compress_struct* cinfo_; | 177 jpeg_compress_struct* cinfo_; |
| 178 }; | 178 }; |
| 179 | 179 |
| 180 } // namespace | 180 } // namespace |
| 181 | 181 |
| 182 bool JPEGCodec::Encode(const unsigned char* input, ColorFormat format, | 182 bool JPEGCodec::Encode(const unsigned char* input, ColorFormat format, |
| 183 int w, int h, int row_byte_width, | 183 int w, int h, int row_byte_width, |
| 184 int quality, std::vector<unsigned char>* output) { | 184 int quality, std::vector<unsigned char>* output) { |
| 185 jpeg_compress_struct cinfo; | 185 jpeg_compress_struct cinfo; |
| 186 CompressDestroyer destroyer; | 186 CompressDestroyer destroyer; |
| 187 destroyer.SetManagedObject(&cinfo); |
| 187 output->clear(); | 188 output->clear(); |
| 188 | 189 |
| 189 // We set up the normal JPEG error routines, then override error_exit. | 190 // We set up the normal JPEG error routines, then override error_exit. |
| 190 // This must be done before the call to create_compress. | 191 // This must be done before the call to create_compress. |
| 191 CoderErrorMgr errmgr; | 192 CoderErrorMgr errmgr; |
| 192 cinfo.err = jpeg_std_error(&errmgr.pub); | 193 cinfo.err = jpeg_std_error(&errmgr.pub); |
| 193 errmgr.pub.error_exit = ErrorExit; | 194 errmgr.pub.error_exit = ErrorExit; |
| 194 // Establish the setjmp return context for ErrorExit to use. | 195 // Establish the setjmp return context for ErrorExit to use. |
| 195 if (setjmp(errmgr.setjmp_buffer)) { | 196 if (setjmp(errmgr.setjmp_buffer)) { |
| 196 // If we get here, the JPEG code has signaled an error. | 197 // If we get here, the JPEG code has signaled an error. |
| 197 // MSDN notes: "if you intend your code to be portable, do not rely on | 198 // MSDN notes: "if you intend your code to be portable, do not rely on |
| 198 // correct destruction of frame-based objects when executing a nonlocal | 199 // correct destruction of frame-based objects when executing a nonlocal |
| 199 // goto using a call to longjmp." So we delete the CompressDestroyer's | 200 // goto using a call to longjmp." So we delete the CompressDestroyer's |
| 200 // object manually instead. | 201 // object manually instead. |
| 201 destroyer.DestroyManagedObject(); | 202 destroyer.DestroyManagedObject(); |
| 202 return false; | 203 return false; |
| 203 } | 204 } |
| 204 | 205 |
| 205 // The destroyer will destroy() cinfo on exit. | 206 // The destroyer will destroy() cinfo on exit. |
| 206 jpeg_create_compress(&cinfo); | 207 jpeg_create_compress(&cinfo); |
| 207 destroyer.SetManagedObject(&cinfo); | |
| 208 | 208 |
| 209 cinfo.image_width = w; | 209 cinfo.image_width = w; |
| 210 cinfo.image_height = h; | 210 cinfo.image_height = h; |
| 211 cinfo.input_components = 3; | 211 cinfo.input_components = 3; |
| 212 cinfo.in_color_space = JCS_RGB; | 212 cinfo.in_color_space = JCS_RGB; |
| 213 cinfo.data_precision = 8; | 213 cinfo.data_precision = 8; |
| 214 | 214 |
| 215 jpeg_set_defaults(&cinfo); | 215 jpeg_set_defaults(&cinfo); |
| 216 jpeg_set_quality(&cinfo, quality, 1); // quality here is 0-100 | 216 jpeg_set_quality(&cinfo, quality, 1); // quality here is 0-100 |
| 217 | 217 |
| (...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 388 jpeg_decompress_struct* cinfo_; | 388 jpeg_decompress_struct* cinfo_; |
| 389 }; | 389 }; |
| 390 | 390 |
| 391 } // namespace | 391 } // namespace |
| 392 | 392 |
| 393 bool JPEGCodec::Decode(const unsigned char* input, size_t input_size, | 393 bool JPEGCodec::Decode(const unsigned char* input, size_t input_size, |
| 394 ColorFormat format, std::vector<unsigned char>* output, | 394 ColorFormat format, std::vector<unsigned char>* output, |
| 395 int* w, int* h) { | 395 int* w, int* h) { |
| 396 jpeg_decompress_struct cinfo; | 396 jpeg_decompress_struct cinfo; |
| 397 DecompressDestroyer destroyer; | 397 DecompressDestroyer destroyer; |
| 398 destroyer.SetManagedObject(&cinfo); |
| 398 output->clear(); | 399 output->clear(); |
| 399 | 400 |
| 400 // We set up the normal JPEG error routines, then override error_exit. | 401 // We set up the normal JPEG error routines, then override error_exit. |
| 401 // This must be done before the call to create_decompress. | 402 // This must be done before the call to create_decompress. |
| 402 CoderErrorMgr errmgr; | 403 CoderErrorMgr errmgr; |
| 403 cinfo.err = jpeg_std_error(&errmgr.pub); | 404 cinfo.err = jpeg_std_error(&errmgr.pub); |
| 404 errmgr.pub.error_exit = ErrorExit; | 405 errmgr.pub.error_exit = ErrorExit; |
| 405 // Establish the setjmp return context for ErrorExit to use. | 406 // Establish the setjmp return context for ErrorExit to use. |
| 406 if (setjmp(errmgr.setjmp_buffer)) { | 407 if (setjmp(errmgr.setjmp_buffer)) { |
| 407 // If we get here, the JPEG code has signaled an error. | 408 // If we get here, the JPEG code has signaled an error. |
| 408 // See note in JPEGCodec::Encode() for why we need to destroy the cinfo | 409 // See note in JPEGCodec::Encode() for why we need to destroy the cinfo |
| 409 // manually here. | 410 // manually here. |
| 410 destroyer.DestroyManagedObject(); | 411 destroyer.DestroyManagedObject(); |
| 411 return false; | 412 return false; |
| 412 } | 413 } |
| 413 | 414 |
| 414 // The destroyer will destroy() cinfo on exit. We don't want to set the | 415 // The destroyer will destroy() cinfo on exit. We don't want to set the |
| 415 // destroyer's object until cinfo is initialized. | 416 // destroyer's object until cinfo is initialized. |
| 416 jpeg_create_decompress(&cinfo); | 417 jpeg_create_decompress(&cinfo); |
| 417 destroyer.SetManagedObject(&cinfo); | |
| 418 | 418 |
| 419 // set up the source manager | 419 // set up the source manager |
| 420 jpeg_source_mgr srcmgr; | 420 jpeg_source_mgr srcmgr; |
| 421 srcmgr.init_source = InitSource; | 421 srcmgr.init_source = InitSource; |
| 422 srcmgr.fill_input_buffer = FillInputBuffer; | 422 srcmgr.fill_input_buffer = FillInputBuffer; |
| 423 srcmgr.skip_input_data = SkipInputData; | 423 srcmgr.skip_input_data = SkipInputData; |
| 424 srcmgr.resync_to_restart = jpeg_resync_to_restart; // use default routine | 424 srcmgr.resync_to_restart = jpeg_resync_to_restart; // use default routine |
| 425 srcmgr.term_source = TermSource; | 425 srcmgr.term_source = TermSource; |
| 426 cinfo.src = &srcmgr; | 426 cinfo.src = &srcmgr; |
| 427 | 427 |
| (...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 514 // Skia only handles 32 bit images. | 514 // Skia only handles 32 bit images. |
| 515 int data_length = w * h * 4; | 515 int data_length = w * h * 4; |
| 516 | 516 |
| 517 SkBitmap* bitmap = new SkBitmap(); | 517 SkBitmap* bitmap = new SkBitmap(); |
| 518 bitmap->setConfig(SkBitmap::kARGB_8888_Config, w, h); | 518 bitmap->setConfig(SkBitmap::kARGB_8888_Config, w, h); |
| 519 bitmap->allocPixels(); | 519 bitmap->allocPixels(); |
| 520 memcpy(bitmap->getAddr32(0, 0), &data_vector[0], data_length); | 520 memcpy(bitmap->getAddr32(0, 0), &data_vector[0], data_length); |
| 521 | 521 |
| 522 return bitmap; | 522 return bitmap; |
| 523 } | 523 } |
| OLD | NEW |