1 /*
2  * Copyright 2011 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 SkImageEncoder_DEFINED
9 #define SkImageEncoder_DEFINED
10 
11 #include "SkImageInfo.h"
12 #include "SkTRegistry.h"
13 
14 class SkBitmap;
15 class SkPixelSerializer;
16 class SkPixmap;
17 class SkData;
18 class SkWStream;
19 
20 class SkImageEncoder {
21 public:
22     // TODO (scroggo): Merge with SkEncodedFormat.
23     enum Type {
24         kUnknown_Type,
25         kBMP_Type,
26         kGIF_Type,
27         kICO_Type,
28         kJPEG_Type,
29         kPNG_Type,
30         kWBMP_Type,
31         kWEBP_Type,
32         kKTX_Type,
33     };
34     static SkImageEncoder* Create(Type);
35 
36     virtual ~SkImageEncoder();
37 
38     /*  Quality ranges from 0..100 */
39     enum {
40         kDefaultQuality = 80
41     };
42 
43     /**
44      *  Encode bitmap 'bm', returning the results in an SkData, at quality level
45      *  'quality' (which can be in range 0-100). If the bitmap cannot be
46      *  encoded, return null. On success, the caller is responsible for
47      *  calling unref() on the data when they are finished.
48      */
49     SkData* encodeData(const SkBitmap&, int quality);
50 
51     /**
52      * Encode bitmap 'bm' in the desired format, writing results to
53      * file 'file', at quality level 'quality' (which can be in range
54      * 0-100). Returns false on failure.
55      */
56     bool encodeFile(const char file[], const SkBitmap& bm, int quality);
57 
58     /**
59      * Encode bitmap 'bm' in the desired format, writing results to
60      * stream 'stream', at quality level 'quality' (which can be in
61      * range 0-100). Returns false on failure.
62      */
63     bool encodeStream(SkWStream* stream, const SkBitmap& bm, int quality);
64 
65     static SkData* EncodeData(const SkImageInfo&, const void* pixels, size_t rowBytes,
66                               Type, int quality);
67     static SkData* EncodeData(const SkBitmap&, Type, int quality);
68 
69     static SkData* EncodeData(const SkPixmap&, Type, int quality);
70 
71     static bool EncodeFile(const char file[], const SkBitmap&, Type,
72                            int quality);
73     static bool EncodeStream(SkWStream*, const SkBitmap&, Type,
74                            int quality);
75 
76     /** Uses SkImageEncoder to serialize images that are not already
77         encoded as SkImageEncoder::kPNG_Type images. */
78     static SkPixelSerializer* CreatePixelSerializer();
79 
80 protected:
81     /**
82      * Encode bitmap 'bm' in the desired format, writing results to
83      * stream 'stream', at quality level 'quality' (which can be in
84      * range 0-100).
85      *
86      * This must be overridden by each SkImageEncoder implementation.
87      */
88     virtual bool onEncode(SkWStream* stream, const SkBitmap& bm, int quality) = 0;
89 };
90 
91 // This macro declares a global (i.e., non-class owned) creation entry point
92 // for each encoder (e.g., CreateJPEGImageEncoder)
93 #define DECLARE_ENCODER_CREATOR(codec)          \
94     SkImageEncoder *Create ## codec ();
95 
96 // This macro defines the global creation entry point for each encoder. Each
97 // encoder implementation that registers with the encoder factory must call it.
98 #define DEFINE_ENCODER_CREATOR(codec) \
99     SkImageEncoder* Create##codec() { return new Sk##codec; }
100 
101 // All the encoders known by Skia. Note that, depending on the compiler settings,
102 // not all of these will be available
103 /** An ARGBImageEncoder will always write out
104  *  bitmap.width() * bitmap.height() * 4
105  *  bytes.
106  */
107 DECLARE_ENCODER_CREATOR(ARGBImageEncoder);
108 DECLARE_ENCODER_CREATOR(JPEGImageEncoder);
109 DECLARE_ENCODER_CREATOR(PNGImageEncoder);
110 DECLARE_ENCODER_CREATOR(KTXImageEncoder);
111 DECLARE_ENCODER_CREATOR(WEBPImageEncoder);
112 
113 #ifdef SK_BUILD_FOR_IOS
114 DECLARE_ENCODER_CREATOR(PNGImageEncoder_IOS);
115 #endif
116 
117 // Typedef to make registering encoder callback easier
118 // This has to be defined outside SkImageEncoder. :(
119 typedef SkTRegistry<SkImageEncoder*(*)(SkImageEncoder::Type)> SkImageEncoder_EncodeReg;
120 #endif
121