OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2015 Google Inc. | 2 * Copyright 2015 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #ifndef SkCodec_DEFINED | 8 #ifndef SkCodec_DEFINED |
9 #define SkCodec_DEFINED | 9 #define SkCodec_DEFINED |
10 | 10 |
| 11 #include <functional> |
| 12 |
11 #include "../private/SkTemplates.h" | 13 #include "../private/SkTemplates.h" |
12 #include "SkColor.h" | 14 #include "SkColor.h" |
13 #include "SkEncodedFormat.h" | 15 #include "SkEncodedFormat.h" |
14 #include "SkEncodedInfo.h" | 16 #include "SkEncodedInfo.h" |
15 #include "SkImageInfo.h" | 17 #include "SkImageInfo.h" |
16 #include "SkSize.h" | 18 #include "SkSize.h" |
17 #include "SkStream.h" | 19 #include "SkStream.h" |
18 #include "SkTypes.h" | 20 #include "SkTypes.h" |
19 #include "SkYUVSizeInfo.h" | 21 #include "SkYUVSizeInfo.h" |
20 | 22 |
21 class SkColorSpace; | 23 class SkColorSpace; |
22 class SkData; | 24 class SkData; |
23 class SkPngChunkReader; | 25 class SkPngChunkReader; |
24 class SkSampler; | 26 class SkSampler; |
25 | 27 |
| 28 namespace DM { |
| 29 class CodecSrc; |
| 30 } |
| 31 |
26 /** | 32 /** |
27 * Abstraction layer directly on top of an image codec. | 33 * Abstraction layer directly on top of an image codec. |
28 */ | 34 */ |
29 class SkCodec : SkNoncopyable { | 35 class SkCodec : SkNoncopyable { |
30 public: | 36 public: |
31 /** | 37 /** |
32 * Minimum number of bytes that must be buffered in SkStream input. | 38 * Minimum number of bytes that must be buffered in SkStream input. |
33 * | 39 * |
34 * An SkStream passed to NewFromStream must be able to use this many | 40 * An SkStream passed to NewFromStream must be able to use this many |
35 * bytes to determine the image type. Then the same SkStream must be | 41 * bytes to determine the image type. Then the same SkStream must be |
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
345 return kCouldNotRewind; | 351 return kCouldNotRewind; |
346 } | 352 } |
347 | 353 |
348 return this->onGetYUV8Planes(sizeInfo, planes); | 354 return this->onGetYUV8Planes(sizeInfo, planes); |
349 } | 355 } |
350 | 356 |
351 /** | 357 /** |
352 * The remaining functions revolve around decoding scanlines. | 358 * The remaining functions revolve around decoding scanlines. |
353 */ | 359 */ |
354 | 360 |
| 361 |
| 362 /** |
| 363 * Prepare for an incremental decode with the specified options. |
| 364 * |
| 365 * This may require a rewind. |
| 366 * |
| 367 * @param dstInfo Info of the destination. If the dimensions do not match |
| 368 * those of getInfo, this implies a scale. |
| 369 * @param options Contains decoding options, including if memory is zero |
| 370 * initialized. |
| 371 * The callback will only be called for rows in the subset specified |
| 372 * by fSubset. |
| 373 * @param ctable A pointer to a color table. When dstInfo.colorType() is |
| 374 * kIndex8, this should be non-NULL and have enough storage for 256 |
| 375 * colors. The color table will be populated after decoding the palett
e. |
| 376 * @param ctableCount A pointer to the size of the color table. When |
| 377 * dstInfo.colorType() is kIndex8, this should be non-NULL. It will |
| 378 * be modified to the true size of the color table (<= 256) after |
| 379 * decoding the palette. |
| 380 * @return Enum representing success or reason for failure. |
| 381 */ |
| 382 Result startIncrementalDecode(const SkImageInfo& dstInfo, const SkCodec::Opt
ions* = nullptr, |
| 383 SkPMColor* ctable = nullptr, int* ctableCount = nullptr); |
| 384 |
| 385 /** |
| 386 * Start/continue the incremental decode. |
| 387 * |
| 388 * Not valid to call before calling startIncrementalDecode(). |
| 389 * |
| 390 * After the first call, should only be called again if more data has been |
| 391 * provided to the source SkStream. |
| 392 * |
| 393 * Unlike getPixels and getScanlines, this does not do any filling. This is |
| 394 * left up to the caller, since they may be skipping lines or continuing th
e |
| 395 * decode later. In the latter case, they may choose to initialize all line
s |
| 396 * first, or only initialize the remaining lines after the first call. |
| 397 * |
| 398 * @param callback This will be called each time a row has been decoded. |
| 399 * The int parameter will be the number of the row (in the Options.fSub
set's |
| 400 * [fTop, fBottom), provided in startIncrementalDecode). |
| 401 * The callback should return either a block of memory to write the row
or |
| 402 * null to skip writing this row. |
| 403 * On consecutive calls, this should always write to the same memory. |
| 404 * @param rowsDecoded Optional output variable returning the total number o
f |
| 405 * lines initialized. This includes all lines decoded from the image, w
hether |
| 406 * or not the client (via the callback) included it in the output, sinc
e |
| 407 * the last call to startIncrementalDecode. Only meaningful if this met
hod |
| 408 * returns kIncompleteInput. Otherwise the implementation may not set i
t. |
| 409 * Note that some implementations may have initialized this many rows,
but |
| 410 * not necessarily finished those rows (e.g. interlaced PNG). This is |
| 411 * useful for determining what rows the client needs to initialize. |
| 412 * @return kSuccess if all lines requested in startIncrementalDecode have |
| 413 * been completely decoded. kIncompleteInput otherwise. |
| 414 */ |
| 415 Result incrementalDecode(std::function<void*(int)> callback, |
| 416 int* rowsDecoded = nullptr) { |
| 417 if (!fStartedIncrementalDecode) { |
| 418 return kInvalidParameters; |
| 419 } |
| 420 return this->onIncrementalDecode(callback, rowsDecoded); |
| 421 } |
| 422 |
355 /** | 423 /** |
356 * Prepare for a scanline decode with the specified options. | 424 * Prepare for a scanline decode with the specified options. |
357 * | 425 * |
358 * After this call, this class will be ready to decode the first scanline. | 426 * After this call, this class will be ready to decode the first scanline. |
359 * | 427 * |
360 * This must be called in order to call getScanlines or skipScanlines. | 428 * This must be called in order to call getScanlines or skipScanlines. |
361 * | 429 * |
362 * This may require rewinding the stream. | 430 * This may require rewinding the stream. |
363 * | 431 * |
364 * Not all SkCodecs support this. | 432 * Not all SkCodecs support this. |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
461 * they will not be in logical order. If the scanline format is | 529 * they will not be in logical order. If the scanline format is |
462 * kOutOfOrder, the nextScanline() API should be used to determine the | 530 * kOutOfOrder, the nextScanline() API should be used to determine the |
463 * actual y-coordinate of the next output row. | 531 * actual y-coordinate of the next output row. |
464 * | 532 * |
465 * For this scanline ordering, it is advisable to get and skip | 533 * For this scanline ordering, it is advisable to get and skip |
466 * scanlines one at a time. | 534 * scanlines one at a time. |
467 * | 535 * |
468 * Interlaced gifs are an example. | 536 * Interlaced gifs are an example. |
469 */ | 537 */ |
470 kOutOfOrder_SkScanlineOrder, | 538 kOutOfOrder_SkScanlineOrder, |
471 | |
472 /* | |
473 * Indicates that the entire image must be decoded in order to output | |
474 * any amount of scanlines. In this case, it is a REALLY BAD IDEA to | |
475 * request scanlines 1-by-1 or in small chunks. The client should | |
476 * determine which scanlines are needed and ask for all of them in | |
477 * a single call to getScanlines(). | |
478 * | |
479 * Interlaced pngs are an example. | |
480 */ | |
481 kNone_SkScanlineOrder, | |
482 }; | 539 }; |
483 | 540 |
484 /** | 541 /** |
485 * An enum representing the order in which scanlines will be returned by | 542 * An enum representing the order in which scanlines will be returned by |
486 * the scanline decoder. | 543 * the scanline decoder. |
487 * | 544 * |
488 * This is undefined before startScanlineDecode() is called. | 545 * This is undefined before startScanlineDecode() is called. |
489 */ | 546 */ |
490 SkScanlineOrder getScanlineOrder() const { return this->onGetScanlineOrder()
; } | 547 SkScanlineOrder getScanlineOrder() const { return this->onGetScanlineOrder()
; } |
491 | 548 |
(...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
651 const SkImageInfo fSrcInfo; | 708 const SkImageInfo fSrcInfo; |
652 SkAutoTDelete<SkStream> fStream; | 709 SkAutoTDelete<SkStream> fStream; |
653 bool fNeedsRewind; | 710 bool fNeedsRewind; |
654 sk_sp<SkColorSpace> fColorSpace; | 711 sk_sp<SkColorSpace> fColorSpace; |
655 const Origin fOrigin; | 712 const Origin fOrigin; |
656 | 713 |
657 // These fields are only meaningful during scanline decodes. | 714 // These fields are only meaningful during scanline decodes. |
658 SkImageInfo fDstInfo; | 715 SkImageInfo fDstInfo; |
659 SkCodec::Options fOptions; | 716 SkCodec::Options fOptions; |
660 int fCurrScanline; | 717 int fCurrScanline; |
| 718 bool fStartedIncrementalDecode; |
661 | 719 |
662 /** | 720 /** |
663 * Return whether these dimensions are supported as a scale. | 721 * Return whether these dimensions are supported as a scale. |
664 * | 722 * |
665 * The codec may choose to cache the information about scale and subset. | 723 * The codec may choose to cache the information about scale and subset. |
666 * Either way, the same information will be passed to onGetPixels/onStart | 724 * Either way, the same information will be passed to onGetPixels/onStart |
667 * on success. | 725 * on success. |
668 * | 726 * |
669 * This must return true for a size returned from getScaledDimensions. | 727 * This must return true for a size returned from getScaledDimensions. |
670 */ | 728 */ |
671 bool dimensionsSupported(const SkISize& dim) { | 729 bool dimensionsSupported(const SkISize& dim) { |
672 return dim == fSrcInfo.dimensions() || this->onDimensionsSupported(dim); | 730 return dim == fSrcInfo.dimensions() || this->onDimensionsSupported(dim); |
673 } | 731 } |
674 | 732 |
675 // Methods for scanline decoding. | 733 // Methods for scanline decoding. |
676 virtual SkCodec::Result onStartScanlineDecode(const SkImageInfo& /*dstInfo*/
, | 734 virtual SkCodec::Result onStartScanlineDecode(const SkImageInfo& /*dstInfo*/
, |
677 const SkCodec::Options& /*options*/, SkPMColor* /*ctable*/, int* /*c
tableCount*/) { | 735 const SkCodec::Options& /*options*/, SkPMColor* /*ctable*/, int* /*c
tableCount*/) { |
678 return kUnimplemented; | 736 return kUnimplemented; |
679 } | 737 } |
680 | 738 |
| 739 virtual Result onStartIncrementalDecode(const SkImageInfo& /*dstInfo*/, |
| 740 const SkCodec::Options&, SkPMColor*, int*) { |
| 741 return kUnimplemented; |
| 742 } |
| 743 |
| 744 virtual Result onIncrementalDecode(std::function<void*(int)>, int*) { |
| 745 return kUnimplemented; |
| 746 } |
| 747 |
| 748 |
681 virtual bool onSkipScanlines(int /*countLines*/) { return false; } | 749 virtual bool onSkipScanlines(int /*countLines*/) { return false; } |
682 | 750 |
683 virtual int onGetScanlines(void* /*dst*/, int /*countLines*/, size_t /*rowBy
tes*/) { return 0; } | 751 virtual int onGetScanlines(void* /*dst*/, int /*countLines*/, size_t /*rowBy
tes*/) { return 0; } |
684 | 752 |
685 /** | 753 /** |
686 * On an incomplete decode, getPixels() and getScanlines() will call this fu
nction | 754 * On an incomplete decode, getPixels() and getScanlines() will call this fu
nction |
687 * to fill any uinitialized memory. | 755 * to fill any uinitialized memory. |
688 * | 756 * |
689 * @param dstInfo Contains the destination color type | 757 * @param dstInfo Contains the destination color type |
690 * Contains the destination alpha type | 758 * Contains the destination alpha type |
(...skipping 11 matching lines...) Expand all Loading... |
702 /** | 770 /** |
703 * Return an object which will allow forcing scanline decodes to sample in
X. | 771 * Return an object which will allow forcing scanline decodes to sample in
X. |
704 * | 772 * |
705 * May create a sampler, if one is not currently being used. Otherwise, doe
s | 773 * May create a sampler, if one is not currently being used. Otherwise, doe
s |
706 * not affect ownership. | 774 * not affect ownership. |
707 * | 775 * |
708 * Only valid during scanline decoding. | 776 * Only valid during scanline decoding. |
709 */ | 777 */ |
710 virtual SkSampler* getSampler(bool /*createIfNecessary*/) { return nullptr;
} | 778 virtual SkSampler* getSampler(bool /*createIfNecessary*/) { return nullptr;
} |
711 | 779 |
| 780 friend class DM::CodecSrc; // for fillIncompleteImage |
712 friend class SkSampledCodec; | 781 friend class SkSampledCodec; |
713 friend class SkIcoCodec; | 782 friend class SkIcoCodec; |
714 }; | 783 }; |
715 #endif // SkCodec_DEFINED | 784 #endif // SkCodec_DEFINED |
OLD | NEW |