Home | History | Annotate | Download | only in core
      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 SkPictureData_DEFINED
      9 #define SkPictureData_DEFINED
     10 
     11 #include "SkBitmap.h"
     12 #include "SkDrawable.h"
     13 #include "SkPicture.h"
     14 #include "SkPictureContentInfo.h"
     15 #include "SkPictureFlat.h"
     16 
     17 class SkData;
     18 class SkPictureRecord;
     19 class SkPixelSerializer;
     20 class SkReader32;
     21 class SkStream;
     22 class SkWStream;
     23 class SkBBoxHierarchy;
     24 class SkMatrix;
     25 class SkPaint;
     26 class SkPath;
     27 class SkReadBuffer;
     28 class SkTextBlob;
     29 
     30 struct SkPictInfo {
     31     enum Flags {
     32         kCrossProcess_Flag      = 1 << 0,
     33         kScalarIsFloat_Flag     = 1 << 1,
     34         kPtrIs64Bit_Flag        = 1 << 2,
     35     };
     36 
     37     SkPictInfo() : fVersion(~0U) {}
     38 
     39     uint32_t getVersion() const {
     40         SkASSERT(fVersion != ~0U);
     41         return fVersion;
     42     }
     43 
     44     void setVersion(uint32_t version) {
     45         SkASSERT(version != ~0U);
     46         fVersion = version;
     47     }
     48 
     49 public:
     50     char        fMagic[8];
     51 private:
     52     uint32_t    fVersion;
     53 public:
     54     SkRect      fCullRect;
     55     uint32_t    fFlags;
     56 };
     57 
     58 #define SK_PICT_READER_TAG     SkSetFourByteTag('r', 'e', 'a', 'd')
     59 #define SK_PICT_FACTORY_TAG    SkSetFourByteTag('f', 'a', 'c', 't')
     60 #define SK_PICT_TYPEFACE_TAG   SkSetFourByteTag('t', 'p', 'f', 'c')
     61 #define SK_PICT_PICTURE_TAG    SkSetFourByteTag('p', 'c', 't', 'r')
     62 #define SK_PICT_DRAWABLE_TAG   SkSetFourByteTag('d', 'r', 'a', 'w')
     63 
     64 // This tag specifies the size of the ReadBuffer, needed for the following tags
     65 #define SK_PICT_BUFFER_SIZE_TAG     SkSetFourByteTag('a', 'r', 'a', 'y')
     66 // these are all inside the ARRAYS tag
     67 #define SK_PICT_BITMAP_BUFFER_TAG   SkSetFourByteTag('b', 't', 'm', 'p')
     68 #define SK_PICT_PAINT_BUFFER_TAG    SkSetFourByteTag('p', 'n', 't', ' ')
     69 #define SK_PICT_PATH_BUFFER_TAG     SkSetFourByteTag('p', 't', 'h', ' ')
     70 #define SK_PICT_TEXTBLOB_BUFFER_TAG SkSetFourByteTag('b', 'l', 'o', 'b')
     71 #define SK_PICT_VERTICES_BUFFER_TAG SkSetFourByteTag('v', 'e', 'r', 't')
     72 #define SK_PICT_IMAGE_BUFFER_TAG    SkSetFourByteTag('i', 'm', 'a', 'g')
     73 
     74 // Always write this guy last (with no length field afterwards)
     75 #define SK_PICT_EOF_TAG     SkSetFourByteTag('e', 'o', 'f', ' ')
     76 
     77 class SkPictureData {
     78 public:
     79     SkPictureData(const SkPictureRecord& record, const SkPictInfo&);
     80     // Does not affect ownership of SkStream.
     81     static SkPictureData* CreateFromStream(SkStream*,
     82                                            const SkPictInfo&,
     83                                            SkImageDeserializer*,
     84                                            SkTypefacePlayback*);
     85     static SkPictureData* CreateFromBuffer(SkReadBuffer&, const SkPictInfo&);
     86 
     87     virtual ~SkPictureData();
     88 
     89     void serialize(SkWStream*, SkPixelSerializer*, SkRefCntSet*) const;
     90     void flatten(SkWriteBuffer&) const;
     91 
     92     bool containsBitmaps() const;
     93 
     94     bool hasText() const { return fContentInfo.hasText(); }
     95 
     96     int opCount() const { return fContentInfo.numOperations(); }
     97 
     98     const sk_sp<SkData>& opData() const { return fOpData; }
     99 
    100 protected:
    101     explicit SkPictureData(const SkPictInfo& info);
    102 
    103     // Does not affect ownership of SkStream.
    104     bool parseStream(SkStream*, SkImageDeserializer*, SkTypefacePlayback*);
    105     bool parseBuffer(SkReadBuffer& buffer);
    106 
    107 public:
    108     const SkImage* getBitmapAsImage(SkReadBuffer* reader) const {
    109         const int index = reader->readInt();
    110         return reader->validateIndex(index, fBitmapImageCount) ? fBitmapImageRefs[index] : nullptr;
    111     }
    112 
    113     const SkImage* getImage(SkReadBuffer* reader) const {
    114         const int index = reader->readInt();
    115         return reader->validateIndex(index, fImageCount) ? fImageRefs[index] : nullptr;
    116     }
    117 
    118     const SkPath& getPath(SkReadBuffer* reader) const {
    119         const int index = reader->readInt() - 1;
    120         return reader->validateIndex(index, fPaths.count()) ? fPaths[index] : fEmptyPath;
    121     }
    122 
    123     const SkPicture* getPicture(SkReadBuffer* reader) const {
    124         const int index = reader->readInt() - 1;
    125         return reader->validateIndex(index, fPictureCount) ? fPictureRefs[index] : nullptr;
    126     }
    127 
    128     SkDrawable* getDrawable(SkReadBuffer* reader) const {
    129         int index = reader->readInt();
    130         SkASSERT(index > 0 && index <= fDrawableCount);
    131         return fDrawableRefs[index - 1];
    132     }
    133 
    134     const SkPaint* getPaint(SkReadBuffer* reader) const {
    135         const int index = reader->readInt() - 1;
    136         if (index == -1) {  // recorder wrote a zero for no paint (likely drawimage)
    137             return nullptr;
    138         }
    139         return reader->validateIndex(index, fPaints.count()) ? &fPaints[index] : nullptr;
    140     }
    141 
    142     const SkTextBlob* getTextBlob(SkReadBuffer* reader) const {
    143         const int index = reader->readInt() - 1;
    144         return reader->validateIndex(index, fTextBlobCount) ? fTextBlobRefs[index] : nullptr;
    145     }
    146 
    147     const SkVertices* getVertices(SkReadBuffer* reader) const {
    148         const int index = reader->readInt() - 1;
    149         return reader->validateIndex(index, fVerticesCount) ? fVerticesRefs[index] : nullptr;
    150     }
    151 
    152 #if SK_SUPPORT_GPU
    153     /**
    154      * sampleCount is the number of samples-per-pixel or zero if non-MSAA.
    155      * It is defaulted to be zero.
    156      */
    157     bool suitableForGpuRasterization(GrContext* context, const char **reason,
    158                                      int sampleCount = 0) const;
    159 
    160     /**
    161      * Calls getRecommendedSampleCount with GrPixelConfig and dpi to calculate sampleCount
    162      * and then calls the above version of suitableForGpuRasterization
    163      */
    164     bool suitableForGpuRasterization(GrContext* context, const char **reason,
    165                                      GrPixelConfig config, SkScalar dpi) const;
    166 
    167     bool suitableForLayerOptimization() const;
    168 #endif
    169 
    170 private:
    171     void init();
    172 
    173     // these help us with reading/writing
    174     // Does not affect ownership of SkStream.
    175     bool parseStreamTag(SkStream*, uint32_t tag, uint32_t size,
    176                         SkImageDeserializer*, SkTypefacePlayback*);
    177     bool parseBufferTag(SkReadBuffer&, uint32_t tag, uint32_t size);
    178     void flattenToBuffer(SkWriteBuffer&) const;
    179 
    180     SkTArray<SkPaint>  fPaints;
    181     SkTArray<SkPath>   fPaths;
    182 
    183     sk_sp<SkData>   fOpData;    // opcodes and parameters
    184 
    185     const SkPath    fEmptyPath;
    186     const SkBitmap  fEmptyBitmap;
    187 
    188     const SkPicture** fPictureRefs;
    189     int fPictureCount;
    190     SkDrawable** fDrawableRefs;
    191     int fDrawableCount;
    192     const SkTextBlob** fTextBlobRefs;
    193     int fTextBlobCount;
    194     const SkVertices** fVerticesRefs;
    195     int fVerticesCount;
    196     const SkImage** fImageRefs;
    197     int fImageCount;
    198     const SkImage** fBitmapImageRefs;
    199     int fBitmapImageCount;
    200 
    201     SkPictureContentInfo fContentInfo;
    202 
    203     SkTypefacePlayback fTFPlayback;
    204     SkFactoryPlayback* fFactoryPlayback;
    205 
    206     const SkPictInfo fInfo;
    207 
    208     static void WriteFactories(SkWStream* stream, const SkFactorySet& rec);
    209     static void WriteTypefaces(SkWStream* stream, const SkRefCntSet& rec);
    210 
    211     void initForPlayback() const;
    212 };
    213 
    214 #endif
    215