OLD | NEW |
1 | 1 |
2 /* | 2 /* |
3 * Copyright 2006 The Android Open Source Project | 3 * Copyright 2006 The Android Open Source Project |
4 * | 4 * |
5 * Use of this source code is governed by a BSD-style license that can be | 5 * Use of this source code is governed by a BSD-style license that can be |
6 * found in the LICENSE file. | 6 * found in the LICENSE file. |
7 */ | 7 */ |
8 | 8 |
9 | 9 |
10 #include "SkImageDecoder.h" | 10 #include "SkImageDecoder.h" |
11 #include "SkColor.h" | 11 #include "SkColor.h" |
12 #include "SkColorPriv.h" | 12 #include "SkColorPriv.h" |
13 #include "SkStream.h" | 13 #include "SkStream.h" |
14 #include "SkTemplates.h" | 14 #include "SkTemplates.h" |
15 #include "SkPackBits.h" | 15 #include "SkPackBits.h" |
16 | 16 |
17 #include "gif_lib.h" | 17 #include "gif_lib.h" |
18 | 18 |
19 class SkGIFImageDecoder : public SkImageDecoder { | 19 class SkGIFImageDecoder : public SkImageDecoder { |
20 public: | 20 public: |
21 virtual Format getFormat() const SK_OVERRIDE { | 21 virtual Format getFormat() const SK_OVERRIDE { |
22 return kGIF_Format; | 22 return kGIF_Format; |
23 } | 23 } |
24 | 24 |
25 protected: | 25 protected: |
26 virtual bool onDecode(SkStream* stream, SkBitmap* bm, Mode mode) SK_OVERRIDE
; | 26 virtual bool onDecode(SkStreamRewindable* stream, SkBitmap* bm, Mode mode) S
K_OVERRIDE; |
27 | 27 |
28 private: | 28 private: |
29 typedef SkImageDecoder INHERITED; | 29 typedef SkImageDecoder INHERITED; |
30 }; | 30 }; |
31 | 31 |
32 static const uint8_t gStartingIterlaceYValue[] = { | 32 static const uint8_t gStartingIterlaceYValue[] = { |
33 0, 4, 2, 1 | 33 0, 4, 2, 1 |
34 }; | 34 }; |
35 static const uint8_t gDeltaIterlaceYValue[] = { | 35 static const uint8_t gDeltaIterlaceYValue[] = { |
36 8, 8, 4, 2 | 36 8, 8, 4, 2 |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
86 int fCurrY; | 86 int fCurrY; |
87 int fDeltaY; | 87 int fDeltaY; |
88 const uint8_t* fStartYPtr; | 88 const uint8_t* fStartYPtr; |
89 const uint8_t* fDeltaYPtr; | 89 const uint8_t* fDeltaYPtr; |
90 }; | 90 }; |
91 | 91 |
92 /////////////////////////////////////////////////////////////////////////////// | 92 /////////////////////////////////////////////////////////////////////////////// |
93 | 93 |
94 static int DecodeCallBackProc(GifFileType* fileType, GifByteType* out, | 94 static int DecodeCallBackProc(GifFileType* fileType, GifByteType* out, |
95 int size) { | 95 int size) { |
96 SkStream* stream = (SkStream*) fileType->UserData; | 96 SkStreamRewindable* stream = (SkStreamRewindable*) fileType->UserData; |
97 return (int) stream->read(out, size); | 97 return (int) stream->read(out, size); |
98 } | 98 } |
99 | 99 |
100 void CheckFreeExtension(SavedImage* Image) { | 100 void CheckFreeExtension(SavedImage* Image) { |
101 if (Image->ExtensionBlocks) { | 101 if (Image->ExtensionBlocks) { |
102 #if GIFLIB_MAJOR < 5 | 102 #if GIFLIB_MAJOR < 5 |
103 FreeExtension(Image); | 103 FreeExtension(Image); |
104 #else | 104 #else |
105 GifFreeExtensions(&Image->ExtensionBlockCount, &Image->ExtensionBlocks); | 105 GifFreeExtensions(&Image->ExtensionBlockCount, &Image->ExtensionBlocks); |
106 #endif | 106 #endif |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
147 | 147 |
148 static bool error_return(GifFileType* gif, const SkBitmap& bm, | 148 static bool error_return(GifFileType* gif, const SkBitmap& bm, |
149 const char msg[]) { | 149 const char msg[]) { |
150 #if 0 | 150 #if 0 |
151 SkDebugf("libgif error <%s> bitmap [%d %d] pixels %p colortable %p\n", | 151 SkDebugf("libgif error <%s> bitmap [%d %d] pixels %p colortable %p\n", |
152 msg, bm.width(), bm.height(), bm.getPixels(), bm.getColorTable()); | 152 msg, bm.width(), bm.height(), bm.getPixels(), bm.getColorTable()); |
153 #endif | 153 #endif |
154 return false; | 154 return false; |
155 } | 155 } |
156 | 156 |
157 bool SkGIFImageDecoder::onDecode(SkStream* sk_stream, SkBitmap* bm, Mode mode) { | 157 bool SkGIFImageDecoder::onDecode(SkStreamRewindable* sk_stream, SkBitmap* bm, Mo
de mode) { |
158 #if GIFLIB_MAJOR < 5 | 158 #if GIFLIB_MAJOR < 5 |
159 GifFileType* gif = DGifOpen(sk_stream, DecodeCallBackProc); | 159 GifFileType* gif = DGifOpen(sk_stream, DecodeCallBackProc); |
160 #else | 160 #else |
161 GifFileType* gif = DGifOpen(sk_stream, DecodeCallBackProc, NULL); | 161 GifFileType* gif = DGifOpen(sk_stream, DecodeCallBackProc, NULL); |
162 #endif | 162 #endif |
163 if (NULL == gif) { | 163 if (NULL == gif) { |
164 return error_return(gif, *bm, "DGifOpen"); | 164 return error_return(gif, *bm, "DGifOpen"); |
165 } | 165 } |
166 | 166 |
167 SkAutoTCallIProc<GifFileType, DGifCloseFile> acp(gif); | 167 SkAutoTCallIProc<GifFileType, DGifCloseFile> acp(gif); |
(...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
349 } while (recType != TERMINATE_RECORD_TYPE); | 349 } while (recType != TERMINATE_RECORD_TYPE); |
350 | 350 |
351 DONE: | 351 DONE: |
352 return true; | 352 return true; |
353 } | 353 } |
354 | 354 |
355 /////////////////////////////////////////////////////////////////////////////// | 355 /////////////////////////////////////////////////////////////////////////////// |
356 DEFINE_DECODER_CREATOR(GIFImageDecoder); | 356 DEFINE_DECODER_CREATOR(GIFImageDecoder); |
357 /////////////////////////////////////////////////////////////////////////////// | 357 /////////////////////////////////////////////////////////////////////////////// |
358 | 358 |
359 static bool is_gif(SkStream* stream) { | 359 static bool is_gif(SkStreamRewindable* stream) { |
360 char buf[GIF_STAMP_LEN]; | 360 char buf[GIF_STAMP_LEN]; |
361 if (stream->read(buf, GIF_STAMP_LEN) == GIF_STAMP_LEN) { | 361 if (stream->read(buf, GIF_STAMP_LEN) == GIF_STAMP_LEN) { |
362 if (memcmp(GIF_STAMP, buf, GIF_STAMP_LEN) == 0 || | 362 if (memcmp(GIF_STAMP, buf, GIF_STAMP_LEN) == 0 || |
363 memcmp(GIF87_STAMP, buf, GIF_STAMP_LEN) == 0 || | 363 memcmp(GIF87_STAMP, buf, GIF_STAMP_LEN) == 0 || |
364 memcmp(GIF89_STAMP, buf, GIF_STAMP_LEN) == 0) { | 364 memcmp(GIF89_STAMP, buf, GIF_STAMP_LEN) == 0) { |
365 return true; | 365 return true; |
366 } | 366 } |
367 } | 367 } |
368 return false; | 368 return false; |
369 } | 369 } |
370 | 370 |
371 #include "SkTRegistry.h" | 371 #include "SkTRegistry.h" |
372 | 372 |
373 static SkImageDecoder* sk_libgif_dfactory(SkStream* stream) { | 373 static SkImageDecoder* sk_libgif_dfactory(SkStreamRewindable* stream) { |
374 if (is_gif(stream)) { | 374 if (is_gif(stream)) { |
375 return SkNEW(SkGIFImageDecoder); | 375 return SkNEW(SkGIFImageDecoder); |
376 } | 376 } |
377 return NULL; | 377 return NULL; |
378 } | 378 } |
379 | 379 |
380 static SkTRegistry<SkImageDecoder*, SkStream*> gReg(sk_libgif_dfactory); | 380 static SkTRegistry<SkImageDecoder*, SkStreamRewindable*> gReg(sk_libgif_dfactory
); |
381 | 381 |
382 static SkImageDecoder::Format get_format_gif(SkStream* stream) { | 382 static SkImageDecoder::Format get_format_gif(SkStreamRewindable* stream) { |
383 if (is_gif(stream)) { | 383 if (is_gif(stream)) { |
384 return SkImageDecoder::kGIF_Format; | 384 return SkImageDecoder::kGIF_Format; |
385 } | 385 } |
386 return SkImageDecoder::kUnknown_Format; | 386 return SkImageDecoder::kUnknown_Format; |
387 } | 387 } |
388 | 388 |
389 static SkTRegistry<SkImageDecoder::Format, SkStream*> gFormatReg(get_format_gif)
; | 389 static SkTRegistry<SkImageDecoder::Format, SkStreamRewindable*> gFormatReg(get_f
ormat_gif); |
OLD | NEW |