1 /*
2  * Copyright 2015 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SkCodec_DEFINED
9 #define SkCodec_DEFINED
10 
11 #include "include/codec/SkCodecAnimation.h"
12 #include "include/codec/SkEncodedOrigin.h"
13 #include "include/core/SkColor.h"
14 #include "include/core/SkEncodedImageFormat.h"
15 #include "include/core/SkImageInfo.h"
16 #include "include/core/SkPixmap.h"
17 #include "include/core/SkSize.h"
18 #include "include/core/SkStream.h"
19 #include "include/core/SkTypes.h"
20 #include "include/core/SkYUVASizeInfo.h"
21 #include "include/private/SkEncodedInfo.h"
22 #include "include/private/SkNoncopyable.h"
23 #include "include/private/SkTemplates.h"
24 
25 #include <vector>
26 
27 class SkColorSpace;
28 class SkData;
29 class SkFrameHolder;
30 class SkPngChunkReader;
31 class SkSampler;
32 
33 namespace DM {
34 class CodecSrc;
35 class ColorCodecSrc;
36 }
37 
38 /**
39  *  Abstraction layer directly on top of an image codec.
40  */
41 class SK_API SkCodec : SkNoncopyable {
42 public:
43     /**
44      *  Minimum number of bytes that must be buffered in SkStream input.
45      *
46      *  An SkStream passed to NewFromStream must be able to use this many
47      *  bytes to determine the image type. Then the same SkStream must be
48      *  passed to the correct decoder to read from the beginning.
49      *
50      *  This can be accomplished by implementing peek() to support peeking
51      *  this many bytes, or by implementing rewind() to be able to rewind()
52      *  after reading this many bytes.
53      */
MinBufferedBytesNeeded()54     static constexpr size_t MinBufferedBytesNeeded() { return 32; }
55 
56     /**
57      *  Error codes for various SkCodec methods.
58      */
59     enum Result {
60         /**
61          *  General return value for success.
62          */
63         kSuccess,
64         /**
65          *  The input is incomplete. A partial image was generated.
66          */
67         kIncompleteInput,
68         /**
69          *  Like kIncompleteInput, except the input had an error.
70          *
71          *  If returned from an incremental decode, decoding cannot continue,
72          *  even with more data.
73          */
74         kErrorInInput,
75         /**
76          *  The generator cannot convert to match the request, ignoring
77          *  dimensions.
78          */
79         kInvalidConversion,
80         /**
81          *  The generator cannot scale to requested size.
82          */
83         kInvalidScale,
84         /**
85          *  Parameters (besides info) are invalid. e.g. NULL pixels, rowBytes
86          *  too small, etc.
87          */
88         kInvalidParameters,
89         /**
90          *  The input did not contain a valid image.
91          */
92         kInvalidInput,
93         /**
94          *  Fulfilling this request requires rewinding the input, which is not
95          *  supported for this input.
96          */
97         kCouldNotRewind,
98         /**
99          *  An internal error, such as OOM.
100          */
101         kInternalError,
102         /**
103          *  This method is not implemented by this codec.
104          *  FIXME: Perhaps this should be kUnsupported?
105          */
106         kUnimplemented,
107     };
108 
109     /**
110      *  Readable string representing the error code.
111      */
112     static const char* ResultToString(Result);
113 
114     /**
115      * For container formats that contain both still images and image sequences,
116      * instruct the decoder how the output should be selected. (Refer to comments
117      * for each value for more details.)
118      */
119     enum class SelectionPolicy {
120         /**
121          *  If the container format contains both still images and image sequences,
122          *  SkCodec should choose one of the still images. This is the default.
123          */
124         kPreferStillImage,
125         /**
126          *  If the container format contains both still images and image sequences,
127          *  SkCodec should choose one of the image sequences for animation.
128          */
129         kPreferAnimation,
130     };
131 
132     /**
133      *  If this stream represents an encoded image that we know how to decode,
134      *  return an SkCodec that can decode it. Otherwise return NULL.
135      *
136      *  As stated above, this call must be able to peek or read
137      *  MinBufferedBytesNeeded to determine the correct format, and then start
138      *  reading from the beginning. First it will attempt to peek, and it
139      *  assumes that if less than MinBufferedBytesNeeded bytes (but more than
140      *  zero) are returned, this is because the stream is shorter than this,
141      *  so falling back to reading would not provide more data. If peek()
142      *  returns zero bytes, this call will instead attempt to read(). This
143      *  will require that the stream can be rewind()ed.
144      *
145      *  If Result is not NULL, it will be set to either kSuccess if an SkCodec
146      *  is returned or a reason for the failure if NULL is returned.
147      *
148      *  If SkPngChunkReader is not NULL, take a ref and pass it to libpng if
149      *  the image is a png.
150      *
151      *  If the SkPngChunkReader is not NULL then:
152      *      If the image is not a PNG, the SkPngChunkReader will be ignored.
153      *      If the image is a PNG, the SkPngChunkReader will be reffed.
154      *      If the PNG has unknown chunks, the SkPngChunkReader will be used
155      *      to handle these chunks.  SkPngChunkReader will be called to read
156      *      any unknown chunk at any point during the creation of the codec
157      *      or the decode.  Note that if SkPngChunkReader fails to read a
158      *      chunk, this could result in a failure to create the codec or a
159      *      failure to decode the image.
160      *      If the PNG does not contain unknown chunks, the SkPngChunkReader
161      *      will not be used or modified.
162      *
163      *  If NULL is returned, the stream is deleted immediately. Otherwise, the
164      *  SkCodec takes ownership of it, and will delete it when done with it.
165      */
166     static std::unique_ptr<SkCodec> MakeFromStream(
167             std::unique_ptr<SkStream>, Result* = nullptr,
168             SkPngChunkReader* = nullptr,
169             SelectionPolicy selectionPolicy = SelectionPolicy::kPreferStillImage);
170 
171     /**
172      *  If this data represents an encoded image that we know how to decode,
173      *  return an SkCodec that can decode it. Otherwise return NULL.
174      *
175      *  If the SkPngChunkReader is not NULL then:
176      *      If the image is not a PNG, the SkPngChunkReader will be ignored.
177      *      If the image is a PNG, the SkPngChunkReader will be reffed.
178      *      If the PNG has unknown chunks, the SkPngChunkReader will be used
179      *      to handle these chunks.  SkPngChunkReader will be called to read
180      *      any unknown chunk at any point during the creation of the codec
181      *      or the decode.  Note that if SkPngChunkReader fails to read a
182      *      chunk, this could result in a failure to create the codec or a
183      *      failure to decode the image.
184      *      If the PNG does not contain unknown chunks, the SkPngChunkReader
185      *      will not be used or modified.
186      */
187     static std::unique_ptr<SkCodec> MakeFromData(sk_sp<SkData>, SkPngChunkReader* = nullptr);
188 
189     virtual ~SkCodec();
190 
191     /**
192      *  Return a reasonable SkImageInfo to decode into.
193      */
getInfo()194     SkImageInfo getInfo() const { return fEncodedInfo.makeImageInfo(); }
195 
dimensions()196     SkISize dimensions() const { return {fEncodedInfo.width(), fEncodedInfo.height()}; }
bounds()197     SkIRect bounds() const {
198         return SkIRect::MakeWH(fEncodedInfo.width(), fEncodedInfo.height());
199     }
200 
201     /**
202      *  Returns the image orientation stored in the EXIF data.
203      *  If there is no EXIF data, or if we cannot read the EXIF data, returns kTopLeft.
204      */
getOrigin()205     SkEncodedOrigin getOrigin() const { return fOrigin; }
206 
207     /**
208      *  Return a size that approximately supports the desired scale factor.
209      *  The codec may not be able to scale efficiently to the exact scale
210      *  factor requested, so return a size that approximates that scale.
211      *  The returned value is the codec's suggestion for the closest valid
212      *  scale that it can natively support
213      */
getScaledDimensions(float desiredScale)214     SkISize getScaledDimensions(float desiredScale) const {
215         // Negative and zero scales are errors.
216         SkASSERT(desiredScale > 0.0f);
217         if (desiredScale <= 0.0f) {
218             return SkISize::Make(0, 0);
219         }
220 
221         // Upscaling is not supported. Return the original size if the client
222         // requests an upscale.
223         if (desiredScale >= 1.0f) {
224             return this->dimensions();
225         }
226         return this->onGetScaledDimensions(desiredScale);
227     }
228 
229     /**
230      *  Return (via desiredSubset) a subset which can decoded from this codec,
231      *  or false if this codec cannot decode subsets or anything similar to
232      *  desiredSubset.
233      *
234      *  @param desiredSubset In/out parameter. As input, a desired subset of
235      *      the original bounds (as specified by getInfo). If true is returned,
236      *      desiredSubset may have been modified to a subset which is
237      *      supported. Although a particular change may have been made to
238      *      desiredSubset to create something supported, it is possible other
239      *      changes could result in a valid subset.
240      *      If false is returned, desiredSubset's value is undefined.
241      *  @return true if this codec supports decoding desiredSubset (as
242      *      returned, potentially modified)
243      */
getValidSubset(SkIRect * desiredSubset)244     bool getValidSubset(SkIRect* desiredSubset) const {
245         return this->onGetValidSubset(desiredSubset);
246     }
247 
248     /**
249      *  Format of the encoded data.
250      */
getEncodedFormat()251     SkEncodedImageFormat getEncodedFormat() const { return this->onGetEncodedFormat(); }
252 
253     /**
254      *  Whether or not the memory passed to getPixels is zero initialized.
255      */
256     enum ZeroInitialized {
257         /**
258          *  The memory passed to getPixels is zero initialized. The SkCodec
259          *  may take advantage of this by skipping writing zeroes.
260          */
261         kYes_ZeroInitialized,
262         /**
263          *  The memory passed to getPixels has not been initialized to zero,
264          *  so the SkCodec must write all zeroes to memory.
265          *
266          *  This is the default. It will be used if no Options struct is used.
267          */
268         kNo_ZeroInitialized,
269     };
270 
271     /**
272      *  Additional options to pass to getPixels.
273      */
274     struct Options {
OptionsOptions275         Options()
276             : fZeroInitialized(kNo_ZeroInitialized)
277             , fSubset(nullptr)
278             , fFrameIndex(0)
279             , fPriorFrame(kNoFrame)
280         {}
281 
282         ZeroInitialized            fZeroInitialized;
283         /**
284          *  If not NULL, represents a subset of the original image to decode.
285          *  Must be within the bounds returned by getInfo().
286          *  If the EncodedFormat is SkEncodedImageFormat::kWEBP (the only one which
287          *  currently supports subsets), the top and left values must be even.
288          *
289          *  In getPixels and incremental decode, we will attempt to decode the
290          *  exact rectangular subset specified by fSubset.
291          *
292          *  In a scanline decode, it does not make sense to specify a subset
293          *  top or subset height, since the client already controls which rows
294          *  to get and which rows to skip.  During scanline decodes, we will
295          *  require that the subset top be zero and the subset height be equal
296          *  to the full height.  We will, however, use the values of
297          *  subset left and subset width to decode partial scanlines on calls
298          *  to getScanlines().
299          */
300         const SkIRect*             fSubset;
301 
302         /**
303          *  The frame to decode.
304          *
305          *  Only meaningful for multi-frame images.
306          */
307         int                        fFrameIndex;
308 
309         /**
310          *  If not kNoFrame, the dst already contains the prior frame at this index.
311          *
312          *  Only meaningful for multi-frame images.
313          *
314          *  If fFrameIndex needs to be blended with a prior frame (as reported by
315          *  getFrameInfo[fFrameIndex].fRequiredFrame), the client can set this to
316          *  any non-kRestorePrevious frame in [fRequiredFrame, fFrameIndex) to
317          *  indicate that that frame is already in the dst. Options.fZeroInitialized
318          *  is ignored in this case.
319          *
320          *  If set to kNoFrame, the codec will decode any necessary required frame(s) first.
321          */
322         int                        fPriorFrame;
323     };
324 
325     /**
326      *  Decode into the given pixels, a block of memory of size at
327      *  least (info.fHeight - 1) * rowBytes + (info.fWidth *
328      *  bytesPerPixel)
329      *
330      *  Repeated calls to this function should give the same results,
331      *  allowing the PixelRef to be immutable.
332      *
333      *  @param info A description of the format (config, size)
334      *         expected by the caller.  This can simply be identical
335      *         to the info returned by getInfo().
336      *
337      *         This contract also allows the caller to specify
338      *         different output-configs, which the implementation can
339      *         decide to support or not.
340      *
341      *         A size that does not match getInfo() implies a request
342      *         to scale. If the generator cannot perform this scale,
343      *         it will return kInvalidScale.
344      *
345      *         If the info contains a non-null SkColorSpace, the codec
346      *         will perform the appropriate color space transformation.
347      *         If the caller passes in the same color space that was
348      *         reported by the codec, the color space transformation is
349      *         a no-op.
350      *
351      *  If a scanline decode is in progress, scanline mode will end, requiring the client to call
352      *  startScanlineDecode() in order to return to decoding scanlines.
353      *
354      *  @return Result kSuccess, or another value explaining the type of failure.
355      */
356     Result getPixels(const SkImageInfo& info, void* pixels, size_t rowBytes, const Options*);
357 
358     /**
359      *  Simplified version of getPixels() that uses the default Options.
360      */
getPixels(const SkImageInfo & info,void * pixels,size_t rowBytes)361     Result getPixels(const SkImageInfo& info, void* pixels, size_t rowBytes) {
362         return this->getPixels(info, pixels, rowBytes, nullptr);
363     }
364 
365     Result getPixels(const SkPixmap& pm, const Options* opts = nullptr) {
366         return this->getPixels(pm.info(), pm.writable_addr(), pm.rowBytes(), opts);
367     }
368 
369     /**
370      *  If decoding to YUV is supported, this returns true.  Otherwise, this
371      *  returns false and does not modify any of the parameters.
372      *
373      *  @param sizeInfo   Output parameter indicating the sizes and required
374      *                    allocation widths of the Y, U, V, and A planes. Given current codec
375      *                    limitations the size of the A plane will always be 0 and the Y, U, V
376      *                    channels will always be planar.
377      *  @param colorSpace Output parameter.  If non-NULL this is set to kJPEG,
378      *                    otherwise this is ignored.
379      */
queryYUV8(SkYUVASizeInfo * sizeInfo,SkYUVColorSpace * colorSpace)380     bool queryYUV8(SkYUVASizeInfo* sizeInfo, SkYUVColorSpace* colorSpace) const {
381         if (nullptr == sizeInfo) {
382             return false;
383         }
384 
385         bool result = this->onQueryYUV8(sizeInfo, colorSpace);
386         if (result) {
387             for (int i = 0; i <= 2; ++i) {
388                 SkASSERT(sizeInfo->fSizes[i].fWidth > 0 && sizeInfo->fSizes[i].fHeight > 0 &&
389                          sizeInfo->fWidthBytes[i] > 0);
390             }
391             SkASSERT(!sizeInfo->fSizes[3].fWidth &&
392                      !sizeInfo->fSizes[3].fHeight &&
393                      !sizeInfo->fWidthBytes[3]);
394         }
395         return result;
396     }
397 
398     /**
399      *  Returns kSuccess, or another value explaining the type of failure.
400      *  This always attempts to perform a full decode.  If the client only
401      *  wants size, it should call queryYUV8().
402      *
403      *  @param sizeInfo   Needs to exactly match the values returned by the
404      *                    query, except the WidthBytes may be larger than the
405      *                    recommendation (but not smaller).
406      *  @param planes     Memory for each of the Y, U, and V planes.
407      */
getYUV8Planes(const SkYUVASizeInfo & sizeInfo,void * planes[SkYUVASizeInfo::kMaxCount])408     Result getYUV8Planes(const SkYUVASizeInfo& sizeInfo, void* planes[SkYUVASizeInfo::kMaxCount]) {
409         if (!planes || !planes[0] || !planes[1] || !planes[2]) {
410             return kInvalidInput;
411         }
412         SkASSERT(!planes[3]); // TODO: is this a fair assumption?
413 
414         if (!this->rewindIfNeeded()) {
415             return kCouldNotRewind;
416         }
417 
418         return this->onGetYUV8Planes(sizeInfo, planes);
419     }
420 
421     /**
422      *  Prepare for an incremental decode with the specified options.
423      *
424      *  This may require a rewind.
425      *
426      *  If kIncompleteInput is returned, may be called again after more data has
427      *  been provided to the source SkStream.
428      *
429      *  @param dstInfo Info of the destination. If the dimensions do not match
430      *      those of getInfo, this implies a scale.
431      *  @param dst Memory to write to. Needs to be large enough to hold the subset,
432      *      if present, or the full image as described in dstInfo.
433      *  @param options Contains decoding options, including if memory is zero
434      *      initialized and whether to decode a subset.
435      *  @return Enum representing success or reason for failure.
436      */
437     Result startIncrementalDecode(const SkImageInfo& dstInfo, void* dst, size_t rowBytes,
438             const Options*);
439 
startIncrementalDecode(const SkImageInfo & dstInfo,void * dst,size_t rowBytes)440     Result startIncrementalDecode(const SkImageInfo& dstInfo, void* dst, size_t rowBytes) {
441         return this->startIncrementalDecode(dstInfo, dst, rowBytes, nullptr);
442     }
443 
444     /**
445      *  Start/continue the incremental decode.
446      *
447      *  Not valid to call before a call to startIncrementalDecode() returns
448      *  kSuccess.
449      *
450      *  If kIncompleteInput is returned, may be called again after more data has
451      *  been provided to the source SkStream.
452      *
453      *  Unlike getPixels and getScanlines, this does not do any filling. This is
454      *  left up to the caller, since they may be skipping lines or continuing the
455      *  decode later. In the latter case, they may choose to initialize all lines
456      *  first, or only initialize the remaining lines after the first call.
457      *
458      *  @param rowsDecoded Optional output variable returning the total number of
459      *      lines initialized. Only meaningful if this method returns kIncompleteInput.
460      *      Otherwise the implementation may not set it.
461      *      Note that some implementations may have initialized this many rows, but
462      *      not necessarily finished those rows (e.g. interlaced PNG). This may be
463      *      useful for determining what rows the client needs to initialize.
464      *  @return kSuccess if all lines requested in startIncrementalDecode have
465      *      been completely decoded. kIncompleteInput otherwise.
466      */
467     Result incrementalDecode(int* rowsDecoded = nullptr) {
468         if (!fStartedIncrementalDecode) {
469             return kInvalidParameters;
470         }
471         return this->onIncrementalDecode(rowsDecoded);
472     }
473 
474     /**
475      * The remaining functions revolve around decoding scanlines.
476      */
477 
478     /**
479      *  Prepare for a scanline decode with the specified options.
480      *
481      *  After this call, this class will be ready to decode the first scanline.
482      *
483      *  This must be called in order to call getScanlines or skipScanlines.
484      *
485      *  This may require rewinding the stream.
486      *
487      *  Not all SkCodecs support this.
488      *
489      *  @param dstInfo Info of the destination. If the dimensions do not match
490      *      those of getInfo, this implies a scale.
491      *  @param options Contains decoding options, including if memory is zero
492      *      initialized.
493      *  @return Enum representing success or reason for failure.
494      */
495     Result startScanlineDecode(const SkImageInfo& dstInfo, const Options* options);
496 
497     /**
498      *  Simplified version of startScanlineDecode() that uses the default Options.
499      */
startScanlineDecode(const SkImageInfo & dstInfo)500     Result startScanlineDecode(const SkImageInfo& dstInfo) {
501         return this->startScanlineDecode(dstInfo, nullptr);
502     }
503 
504     /**
505      *  Write the next countLines scanlines into dst.
506      *
507      *  Not valid to call before calling startScanlineDecode().
508      *
509      *  @param dst Must be non-null, and large enough to hold countLines
510      *      scanlines of size rowBytes.
511      *  @param countLines Number of lines to write.
512      *  @param rowBytes Number of bytes per row. Must be large enough to hold
513      *      a scanline based on the SkImageInfo used to create this object.
514      *  @return the number of lines successfully decoded.  If this value is
515      *      less than countLines, this will fill the remaining lines with a
516      *      default value.
517      */
518     int getScanlines(void* dst, int countLines, size_t rowBytes);
519 
520     /**
521      *  Skip count scanlines.
522      *
523      *  Not valid to call before calling startScanlineDecode().
524      *
525      *  The default version just calls onGetScanlines and discards the dst.
526      *  NOTE: If skipped lines are the only lines with alpha, this default
527      *  will make reallyHasAlpha return true, when it could have returned
528      *  false.
529      *
530      *  @return true if the scanlines were successfully skipped
531      *          false on failure, possible reasons for failure include:
532      *              An incomplete input image stream.
533      *              Calling this function before calling startScanlineDecode().
534      *              If countLines is less than zero or so large that it moves
535      *                  the current scanline past the end of the image.
536      */
537     bool skipScanlines(int countLines);
538 
539     /**
540      *  The order in which rows are output from the scanline decoder is not the
541      *  same for all variations of all image types.  This explains the possible
542      *  output row orderings.
543      */
544     enum SkScanlineOrder {
545         /*
546          * By far the most common, this indicates that the image can be decoded
547          * reliably using the scanline decoder, and that rows will be output in
548          * the logical order.
549          */
550         kTopDown_SkScanlineOrder,
551 
552         /*
553          * This indicates that the scanline decoder reliably outputs rows, but
554          * they will be returned in reverse order.  If the scanline format is
555          * kBottomUp, the nextScanline() API can be used to determine the actual
556          * y-coordinate of the next output row, but the client is not forced
557          * to take advantage of this, given that it's not too tough to keep
558          * track independently.
559          *
560          * For full image decodes, it is safe to get all of the scanlines at
561          * once, since the decoder will handle inverting the rows as it
562          * decodes.
563          *
564          * For subset decodes and sampling, it is simplest to get and skip
565          * scanlines one at a time, using the nextScanline() API.  It is
566          * possible to ask for larger chunks at a time, but this should be used
567          * with caution.  As with full image decodes, the decoder will handle
568          * inverting the requested rows, but rows will still be delivered
569          * starting from the bottom of the image.
570          *
571          * Upside down bmps are an example.
572          */
573         kBottomUp_SkScanlineOrder,
574     };
575 
576     /**
577      *  An enum representing the order in which scanlines will be returned by
578      *  the scanline decoder.
579      *
580      *  This is undefined before startScanlineDecode() is called.
581      */
getScanlineOrder()582     SkScanlineOrder getScanlineOrder() const { return this->onGetScanlineOrder(); }
583 
584     /**
585      *  Returns the y-coordinate of the next row to be returned by the scanline
586      *  decoder.
587      *
588      *  This will equal fCurrScanline, except in the case of strangely
589      *  encoded image types (bottom-up bmps).
590      *
591      *  Results are undefined when not in scanline decoding mode.
592      */
nextScanline()593     int nextScanline() const { return this->outputScanline(fCurrScanline); }
594 
595     /**
596      *  Returns the output y-coordinate of the row that corresponds to an input
597      *  y-coordinate.  The input y-coordinate represents where the scanline
598      *  is located in the encoded data.
599      *
600      *  This will equal inputScanline, except in the case of strangely
601      *  encoded image types (bottom-up bmps, interlaced gifs).
602      */
603     int outputScanline(int inputScanline) const;
604 
605     /**
606      *  Return the number of frames in the image.
607      *
608      *  May require reading through the stream.
609      */
getFrameCount()610     int getFrameCount() {
611         return this->onGetFrameCount();
612     }
613 
614     // Sentinel value used when a frame index implies "no frame":
615     // - FrameInfo::fRequiredFrame set to this value means the frame
616     //   is independent.
617     // - Options::fPriorFrame set to this value means no (relevant) prior frame
618     //   is residing in dst's memory.
619     static constexpr int kNoFrame = -1;
620 
621     // This transitional definition was added in August 2018, and will eventually be removed.
622 #ifdef SK_LEGACY_SKCODEC_NONE_ENUM
623     static constexpr int kNone = kNoFrame;
624 #endif
625 
626     /**
627      *  Information about individual frames in a multi-framed image.
628      */
629     struct FrameInfo {
630         /**
631          *  The frame that this frame needs to be blended with, or
632          *  kNoFrame if this frame is independent (so it can be
633          *  drawn over an uninitialized buffer).
634          *
635          *  Note that this is the *earliest* frame that can be used
636          *  for blending. Any frame from [fRequiredFrame, i) can be
637          *  used, unless its fDisposalMethod is kRestorePrevious.
638          */
639         int fRequiredFrame;
640 
641         /**
642          *  Number of milliseconds to show this frame.
643          */
644         int fDuration;
645 
646         /**
647          *  Whether the end marker for this frame is contained in the stream.
648          *
649          *  Note: this does not guarantee that an attempt to decode will be complete.
650          *  There could be an error in the stream.
651          */
652         bool fFullyReceived;
653 
654         /**
655          *  This is conservative; it will still return non-opaque if e.g. a
656          *  color index-based frame has a color with alpha but does not use it.
657          */
658         SkAlphaType fAlphaType;
659 
660         /**
661          *  How this frame should be modified before decoding the next one.
662          */
663         SkCodecAnimation::DisposalMethod fDisposalMethod;
664     };
665 
666     /**
667      *  Return info about a single frame.
668      *
669      *  Only supported by multi-frame images. Does not read through the stream,
670      *  so it should be called after getFrameCount() to parse any frames that
671      *  have not already been parsed.
672      */
getFrameInfo(int index,FrameInfo * info)673     bool getFrameInfo(int index, FrameInfo* info) const {
674         if (index < 0) {
675             return false;
676         }
677         return this->onGetFrameInfo(index, info);
678     }
679 
680     /**
681      *  Return info about all the frames in the image.
682      *
683      *  May require reading through the stream to determine info about the
684      *  frames (including the count).
685      *
686      *  As such, future decoding calls may require a rewind.
687      *
688      *  For still (non-animated) image codecs, this will return an empty vector.
689      */
690     std::vector<FrameInfo> getFrameInfo();
691 
692     static constexpr int kRepetitionCountInfinite = -1;
693 
694     /**
695      *  Return the number of times to repeat, if this image is animated. This number does not
696      *  include the first play through of each frame. For example, a repetition count of 4 means
697      *  that each frame is played 5 times and then the animation stops.
698      *
699      *  It can return kRepetitionCountInfinite, a negative number, meaning that the animation
700      *  should loop forever.
701      *
702      *  May require reading the stream to find the repetition count.
703      *
704      *  As such, future decoding calls may require a rewind.
705      *
706      *  For still (non-animated) image codecs, this will return 0.
707      */
getRepetitionCount()708     int getRepetitionCount() {
709         return this->onGetRepetitionCount();
710     }
711 
712     // Register a decoder at runtime by passing two function pointers:
713     //    - peek() to return true if the span of bytes appears to be your encoded format;
714     //    - make() to attempt to create an SkCodec from the given stream.
715     // Not thread safe.
716     static void Register(
717             bool                     (*peek)(const void*, size_t),
718             std::unique_ptr<SkCodec> (*make)(std::unique_ptr<SkStream>, SkCodec::Result*));
719 
720 protected:
getEncodedInfo()721     const SkEncodedInfo& getEncodedInfo() const { return fEncodedInfo; }
722 
723     using XformFormat = skcms_PixelFormat;
724 
725     SkCodec(SkEncodedInfo&&,
726             XformFormat srcFormat,
727             std::unique_ptr<SkStream>,
728             SkEncodedOrigin = kTopLeft_SkEncodedOrigin);
729 
onGetScaledDimensions(float)730     virtual SkISize onGetScaledDimensions(float /*desiredScale*/) const {
731         // By default, scaling is not supported.
732         return this->dimensions();
733     }
734 
735     // FIXME: What to do about subsets??
736     /**
737      *  Subclasses should override if they support dimensions other than the
738      *  srcInfo's.
739      */
onDimensionsSupported(const SkISize &)740     virtual bool onDimensionsSupported(const SkISize&) {
741         return false;
742     }
743 
744     virtual SkEncodedImageFormat onGetEncodedFormat() const = 0;
745 
746     /**
747      * @param rowsDecoded When the encoded image stream is incomplete, this function
748      *                    will return kIncompleteInput and rowsDecoded will be set to
749      *                    the number of scanlines that were successfully decoded.
750      *                    This will allow getPixels() to fill the uninitialized memory.
751      */
752     virtual Result onGetPixels(const SkImageInfo& info,
753                                void* pixels, size_t rowBytes, const Options&,
754                                int* rowsDecoded) = 0;
755 
onQueryYUV8(SkYUVASizeInfo *,SkYUVColorSpace *)756     virtual bool onQueryYUV8(SkYUVASizeInfo*, SkYUVColorSpace*) const {
757         return false;
758     }
759 
onGetYUV8Planes(const SkYUVASizeInfo &,void * [SkYUVASizeInfo::kMaxCount])760     virtual Result onGetYUV8Planes(const SkYUVASizeInfo&,
761                                    void*[SkYUVASizeInfo::kMaxCount] /*planes*/) {
762         return kUnimplemented;
763     }
764 
onGetValidSubset(SkIRect *)765     virtual bool onGetValidSubset(SkIRect* /*desiredSubset*/) const {
766         // By default, subsets are not supported.
767         return false;
768     }
769 
770     /**
771      *  If the stream was previously read, attempt to rewind.
772      *
773      *  If the stream needed to be rewound, call onRewind.
774      *  @returns true if the codec is at the right position and can be used.
775      *      false if there was a failure to rewind.
776      *
777      *  This is called by getPixels(), getYUV8Planes(), startIncrementalDecode() and
778      *  startScanlineDecode(). Subclasses may call if they need to rewind at another time.
779      */
780     bool SK_WARN_UNUSED_RESULT rewindIfNeeded();
781 
782     /**
783      *  Called by rewindIfNeeded, if the stream needed to be rewound.
784      *
785      *  Subclasses should do any set up needed after a rewind.
786      */
onRewind()787     virtual bool onRewind() {
788         return true;
789     }
790 
791     /**
792      * Get method for the input stream
793      */
stream()794     SkStream* stream() {
795         return fStream.get();
796     }
797 
798     /**
799      *  The remaining functions revolve around decoding scanlines.
800      */
801 
802     /**
803      *  Most images types will be kTopDown and will not need to override this function.
804      */
onGetScanlineOrder()805     virtual SkScanlineOrder onGetScanlineOrder() const { return kTopDown_SkScanlineOrder; }
806 
dstInfo()807     const SkImageInfo& dstInfo() const { return fDstInfo; }
808 
options()809     const Options& options() const { return fOptions; }
810 
811     /**
812      *  Returns the number of scanlines that have been decoded so far.
813      *  This is unaffected by the SkScanlineOrder.
814      *
815      *  Returns -1 if we have not started a scanline decode.
816      */
currScanline()817     int currScanline() const { return fCurrScanline; }
818 
819     virtual int onOutputScanline(int inputScanline) const;
820 
821     /**
822      *  Return whether we can convert to dst.
823      *
824      *  Will be called for the appropriate frame, prior to initializing the colorXform.
825      */
826     virtual bool conversionSupported(const SkImageInfo& dst, bool srcIsOpaque,
827                                      bool needsColorXform);
828 
829     // Some classes never need a colorXform e.g.
830     // - ICO uses its embedded codec's colorXform
831     // - WBMP is just Black/White
usesColorXform()832     virtual bool usesColorXform() const { return true; }
833     void applyColorXform(void* dst, const void* src, int count) const;
834 
colorXform()835     bool colorXform() const { return fXformTime != kNo_XformTime; }
xformOnDecode()836     bool xformOnDecode() const { return fXformTime == kDecodeRow_XformTime; }
837 
onGetFrameCount()838     virtual int onGetFrameCount() {
839         return 1;
840     }
841 
onGetFrameInfo(int,FrameInfo *)842     virtual bool onGetFrameInfo(int, FrameInfo*) const {
843         return false;
844     }
845 
onGetRepetitionCount()846     virtual int onGetRepetitionCount() {
847         return 0;
848     }
849 
850 private:
851     const SkEncodedInfo                fEncodedInfo;
852     const XformFormat                  fSrcXformFormat;
853     std::unique_ptr<SkStream>          fStream;
854     bool                               fNeedsRewind;
855     const SkEncodedOrigin              fOrigin;
856 
857     SkImageInfo                        fDstInfo;
858     Options                            fOptions;
859 
860     enum XformTime {
861         kNo_XformTime,
862         kPalette_XformTime,
863         kDecodeRow_XformTime,
864     };
865     XformTime                          fXformTime;
866     XformFormat                        fDstXformFormat; // Based on fDstInfo.
867     skcms_ICCProfile                   fDstProfile;
868     skcms_AlphaFormat                  fDstXformAlphaFormat;
869 
870     // Only meaningful during scanline decodes.
871     int                                fCurrScanline;
872 
873     bool                               fStartedIncrementalDecode;
874 
875     bool initializeColorXform(const SkImageInfo& dstInfo, SkEncodedInfo::Alpha, bool srcIsOpaque);
876 
877     /**
878      *  Return whether these dimensions are supported as a scale.
879      *
880      *  The codec may choose to cache the information about scale and subset.
881      *  Either way, the same information will be passed to onGetPixels/onStart
882      *  on success.
883      *
884      *  This must return true for a size returned from getScaledDimensions.
885      */
dimensionsSupported(const SkISize & dim)886     bool dimensionsSupported(const SkISize& dim) {
887         return dim == this->dimensions() || this->onDimensionsSupported(dim);
888     }
889 
890     /**
891      *  For multi-framed images, return the object with information about the frames.
892      */
getFrameHolder()893     virtual const SkFrameHolder* getFrameHolder() const {
894         return nullptr;
895     }
896 
897     /**
898      *  Check for a valid Options.fFrameIndex, and decode prior frames if necessary.
899      */
900     Result handleFrameIndex(const SkImageInfo&, void* pixels, size_t rowBytes, const Options&);
901 
902     // Methods for scanline decoding.
onStartScanlineDecode(const SkImageInfo &,const Options &)903     virtual Result onStartScanlineDecode(const SkImageInfo& /*dstInfo*/,
904             const Options& /*options*/) {
905         return kUnimplemented;
906     }
907 
onStartIncrementalDecode(const SkImageInfo &,void *,size_t,const Options &)908     virtual Result onStartIncrementalDecode(const SkImageInfo& /*dstInfo*/, void*, size_t,
909             const Options&) {
910         return kUnimplemented;
911     }
912 
onIncrementalDecode(int *)913     virtual Result onIncrementalDecode(int*) {
914         return kUnimplemented;
915     }
916 
917 
onSkipScanlines(int)918     virtual bool onSkipScanlines(int /*countLines*/) { return false; }
919 
onGetScanlines(void *,int,size_t)920     virtual int onGetScanlines(void* /*dst*/, int /*countLines*/, size_t /*rowBytes*/) { return 0; }
921 
922     /**
923      * On an incomplete decode, getPixels() and getScanlines() will call this function
924      * to fill any uinitialized memory.
925      *
926      * @param dstInfo        Contains the destination color type
927      *                       Contains the destination alpha type
928      *                       Contains the destination width
929      *                       The height stored in this info is unused
930      * @param dst            Pointer to the start of destination pixel memory
931      * @param rowBytes       Stride length in destination pixel memory
932      * @param zeroInit       Indicates if memory is zero initialized
933      * @param linesRequested Number of lines that the client requested
934      * @param linesDecoded   Number of lines that were successfully decoded
935      */
936     void fillIncompleteImage(const SkImageInfo& dstInfo, void* dst, size_t rowBytes,
937             ZeroInitialized zeroInit, int linesRequested, int linesDecoded);
938 
939     /**
940      *  Return an object which will allow forcing scanline decodes to sample in X.
941      *
942      *  May create a sampler, if one is not currently being used. Otherwise, does
943      *  not affect ownership.
944      *
945      *  Only valid during scanline decoding or incremental decoding.
946      */
getSampler(bool)947     virtual SkSampler* getSampler(bool /*createIfNecessary*/) { return nullptr; }
948 
949     friend class DM::CodecSrc;  // for fillIncompleteImage
950     friend class SkSampledCodec;
951     friend class SkIcoCodec;
952     friend class SkAndroidCodec; // for fEncodedInfo
953 };
954 #endif // SkCodec_DEFINED
955