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 SkJpegCodec_DEFINED 9 #define SkJpegCodec_DEFINED 10 11 #include "SkCodec.h" 12 #include "SkImageInfo.h" 13 #include "SkJpegDecoderMgr.h" 14 #include "SkJpegUtility.h" 15 #include "SkStream.h" 16 17 extern "C" { 18 #include "jpeglib.h" 19 } 20 21 /* 22 * 23 * This class implements the decoding for jpeg images 24 * 25 */ 26 class SkJpegCodec : public SkCodec { 27 public: 28 29 /* 30 * Checks the start of the stream to see if the image is a jpeg 31 * Does not take ownership of the stream 32 */ 33 static bool IsJpeg(SkStream*); 34 35 /* 36 * Assumes IsJpeg was called and returned true 37 * Creates a jpeg decoder 38 * Takes ownership of the stream 39 */ 40 static SkCodec* NewFromStream(SkStream*); 41 42 protected: 43 44 /* 45 * Recommend a set of destination dimensions given a requested scale 46 */ 47 SkISize onGetScaledDimensions(float desiredScale) const override; 48 49 /* 50 * Initiates the jpeg decode 51 */ 52 Result onGetPixels(const SkImageInfo& dstInfo, void* dst, size_t dstRowBytes, const Options&, 53 SkPMColor*, int*) override; 54 onGetEncodedFormat()55 SkEncodedFormat onGetEncodedFormat() const override { 56 return kJPEG_SkEncodedFormat; 57 } 58 59 SkScanlineDecoder* onGetScanlineDecoder(const SkImageInfo& dstInfo, const Options& options, 60 SkPMColor ctable[], int* ctableCount) override; 61 62 private: 63 64 /* 65 * Read enough of the stream to initialize the SkJpegCodec. 66 * Returns a bool representing success or failure. 67 * 68 * @param codecOut 69 * If this returns true, and codecOut was not NULL, 70 * codecOut will be set to a new SkJpegCodec. 71 * 72 * @param decoderMgrOut 73 * If this returns true, and codecOut was NULL, 74 * decoderMgrOut must be non-NULL and decoderMgrOut will be set to a new 75 * JpegDecoderMgr pointer. 76 * 77 * @param stream 78 * Deleted on failure. 79 * codecOut will take ownership of it in the case where we created a codec. 80 * Ownership is unchanged when we set decoderMgrOut. 81 * 82 */ 83 static bool ReadHeader(SkStream* stream, SkCodec** codecOut, 84 JpegDecoderMgr** decoderMgrOut); 85 86 /* 87 * Creates an instance of the decoder 88 * Called only by NewFromStream 89 * 90 * @param srcInfo contains the source width and height 91 * @param stream the encoded image data 92 * @param decoderMgr holds decompress struct, src manager, and error manager 93 * takes ownership 94 */ 95 SkJpegCodec(const SkImageInfo& srcInfo, SkStream* stream, JpegDecoderMgr* decoderMgr); 96 97 /* 98 * Handles rewinding the input stream if it is necessary 99 */ 100 bool handleRewind(); 101 102 /* 103 * Checks if we can scale to the requested dimensions and scales the dimensions 104 * if possible 105 */ 106 bool scaleToDimensions(uint32_t width, uint32_t height); 107 108 /* 109 * Create the swizzler based on the encoded format 110 */ 111 void initializeSwizzler(const SkImageInfo& dstInfo, void* dst, size_t dstRowBytes, 112 const Options& options); 113 114 SkAutoTDelete<JpegDecoderMgr> fDecoderMgr; 115 SkAutoTDelete<SkSwizzler> fSwizzler; 116 size_t fSrcRowBytes; 117 118 friend class SkJpegScanlineDecoder; 119 120 typedef SkCodec INHERITED; 121 }; 122 123 #endif 124