Home | History | Annotate | Download | only in core
      1 
      2 /*
      3  * Copyright 2011 Google Inc.
      4  *
      5  * Use of this source code is governed by a BSD-style license that can be
      6  * found in the LICENSE file.
      7  */
      8 #include "SkPictureFlat.h"
      9 
     10 #include "SkColorFilter.h"
     11 #include "SkDrawLooper.h"
     12 #include "SkMaskFilter.h"
     13 #include "SkRasterizer.h"
     14 #include "SkShader.h"
     15 #include "SkTypeface.h"
     16 #include "SkXfermode.h"
     17 
     18 SkFlatData* SkFlatData::Alloc(SkChunkAlloc* heap, int32_t size, int index) {
     19     SkFlatData* result = (SkFlatData*) heap->allocThrow(size + sizeof(SkFlatData));
     20     result->fIndex = index;
     21     result->fAllocSize = size + sizeof(result->fAllocSize);
     22     return result;
     23 }
     24 
     25 SkFlatBitmap* SkFlatBitmap::Flatten(SkChunkAlloc* heap, const SkBitmap& bitmap,
     26                                     int index, SkRefCntSet* rec) {
     27     SkFlattenableWriteBuffer buffer(1024);
     28     buffer.setRefCntRecorder(rec);
     29 
     30     bitmap.flatten(buffer);
     31     size_t size = buffer.size();
     32     SkFlatBitmap* result = (SkFlatBitmap*) INHERITED::Alloc(heap, size, index);
     33     buffer.flatten(result->fBitmapData);
     34     return result;
     35 }
     36 
     37 SkFlatMatrix* SkFlatMatrix::Flatten(SkChunkAlloc* heap, const SkMatrix& matrix, int index) {
     38     size_t size = matrix.flatten(NULL);
     39     SkFlatMatrix* result = (SkFlatMatrix*) INHERITED::Alloc(heap, size, index);
     40     matrix.flatten(&result->fMatrixData);
     41     return result;
     42 }
     43 
     44 #ifdef SK_DEBUG_DUMP
     45 void SkFlatMatrix::dump() const {
     46     const SkMatrix* matrix = (const SkMatrix*) fMatrixData;
     47     char pBuffer[DUMP_BUFFER_SIZE];
     48     char* bufferPtr = pBuffer;
     49     bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     50     "matrix: ");
     51     SkScalar scaleX = matrix->getScaleX();
     52     SkMatrix defaultMatrix;
     53     defaultMatrix.reset();
     54     if (scaleX != defaultMatrix.getScaleX())
     55         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     56             "scaleX:%g ", SkScalarToFloat(scaleX));
     57     SkScalar scaleY = matrix->getScaleY();
     58     if (scaleY != defaultMatrix.getScaleY())
     59         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     60             "scaleY:%g ", SkScalarToFloat(scaleY));
     61     SkScalar skewX = matrix->getSkewX();
     62     if (skewX != defaultMatrix.getSkewX())
     63         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     64             "skewX:%g ", SkScalarToFloat(skewX));
     65     SkScalar skewY = matrix->getSkewY();
     66     if (skewY != defaultMatrix.getSkewY())
     67         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     68             "skewY:%g ", SkScalarToFloat(skewY));
     69     SkScalar translateX = matrix->getTranslateX();
     70     if (translateX != defaultMatrix.getTranslateX())
     71         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     72             "translateX:%g ", SkScalarToFloat(translateX));
     73     SkScalar translateY = matrix->getTranslateY();
     74     if (translateY != defaultMatrix.getTranslateY())
     75         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     76             "translateY:%g ", SkScalarToFloat(translateY));
     77     SkScalar perspX = matrix->getPerspX();
     78     if (perspX != defaultMatrix.getPerspX())
     79         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     80             "perspX:%g ", SkFractToFloat(perspX));
     81     SkScalar perspY = matrix->getPerspY();
     82     if (perspY != defaultMatrix.getPerspY())
     83         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
     84             "perspY:%g ", SkFractToFloat(perspY));
     85     SkDebugf("%s\n", pBuffer);
     86 }
     87 #endif
     88 
     89 ///////////////////////////////////////////////////////////////////////////////
     90 
     91 SkFlatPaint* SkFlatPaint::Flatten(SkChunkAlloc* heap, const SkPaint& paint,
     92                                   int index, SkRefCntSet* rec,
     93                                   SkRefCntSet* faceRecorder) {
     94     SkFlattenableWriteBuffer buffer(2*sizeof(SkPaint));
     95     buffer.setRefCntRecorder(rec);
     96     buffer.setTypefaceRecorder(faceRecorder);
     97 
     98     paint.flatten(buffer);
     99     uint32_t size = buffer.size();
    100     SkFlatPaint* result = (SkFlatPaint*) INHERITED::Alloc(heap, size, index);
    101     buffer.flatten(&result->fPaintData);
    102     return result;
    103 }
    104 
    105 void SkFlatPaint::Read(const void* storage, SkPaint* paint,
    106                    SkRefCntPlayback* rcp, SkTypefacePlayback* facePlayback) {
    107     SkFlattenableReadBuffer buffer(storage);
    108     if (rcp) {
    109         rcp->setupBuffer(buffer);
    110     }
    111     if (facePlayback) {
    112         facePlayback->setupBuffer(buffer);
    113     }
    114     paint->unflatten(buffer);
    115 }
    116 
    117 #ifdef SK_DEBUG_DUMP
    118 void SkFlatPaint::dump() const {
    119     SkPaint defaultPaint;
    120     SkFlattenableReadBuffer buffer(fPaintData);
    121     SkTypeface* typeface = (SkTypeface*) buffer.readPtr();
    122     char pBuffer[DUMP_BUFFER_SIZE];
    123     char* bufferPtr = pBuffer;
    124     bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    125         "paint: ");
    126     if (typeface != defaultPaint.getTypeface())
    127         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    128             "typeface:%p ", typeface);
    129     SkScalar textSize = buffer.readScalar();
    130     if (textSize != defaultPaint.getTextSize())
    131         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    132             "textSize:%g ", SkScalarToFloat(textSize));
    133     SkScalar textScaleX = buffer.readScalar();
    134     if (textScaleX != defaultPaint.getTextScaleX())
    135         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    136             "textScaleX:%g ", SkScalarToFloat(textScaleX));
    137     SkScalar textSkewX = buffer.readScalar();
    138     if (textSkewX != defaultPaint.getTextSkewX())
    139         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    140             "textSkewX:%g ", SkScalarToFloat(textSkewX));
    141     const SkPathEffect* pathEffect = (const SkPathEffect*) buffer.readFlattenable();
    142     if (pathEffect != defaultPaint.getPathEffect())
    143         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    144             "pathEffect:%p ", pathEffect);
    145     SkDELETE(pathEffect);
    146     const SkShader* shader = (const SkShader*) buffer.readFlattenable();
    147     if (shader != defaultPaint.getShader())
    148         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    149             "shader:%p ", shader);
    150     SkDELETE(shader);
    151     const SkXfermode* xfermode = (const SkXfermode*) buffer.readFlattenable();
    152     if (xfermode != defaultPaint.getXfermode())
    153         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    154             "xfermode:%p ", xfermode);
    155     SkDELETE(xfermode);
    156     const SkMaskFilter* maskFilter = (const SkMaskFilter*) buffer.readFlattenable();
    157     if (maskFilter != defaultPaint.getMaskFilter())
    158         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    159             "maskFilter:%p ", maskFilter);
    160     SkDELETE(maskFilter);
    161     const SkColorFilter* colorFilter = (const SkColorFilter*) buffer.readFlattenable();
    162     if (colorFilter != defaultPaint.getColorFilter())
    163         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    164             "colorFilter:%p ", colorFilter);
    165     SkDELETE(colorFilter);
    166     const SkRasterizer* rasterizer = (const SkRasterizer*) buffer.readFlattenable();
    167     if (rasterizer != defaultPaint.getRasterizer())
    168         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    169             "rasterizer:%p ", rasterizer);
    170     SkDELETE(rasterizer);
    171     const SkDrawLooper* drawLooper = (const SkDrawLooper*) buffer.readFlattenable();
    172     if (drawLooper != defaultPaint.getLooper())
    173         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    174             "drawLooper:%p ", drawLooper);
    175     SkDELETE(drawLooper);
    176     unsigned color = buffer.readU32();
    177     if (color != defaultPaint.getColor())
    178         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    179             "color:0x%x ", color);
    180     SkScalar strokeWidth = buffer.readScalar();
    181     if (strokeWidth != defaultPaint.getStrokeWidth())
    182         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    183             "strokeWidth:%g ", SkScalarToFloat(strokeWidth));
    184     SkScalar strokeMiter = buffer.readScalar();
    185     if (strokeMiter != defaultPaint.getStrokeMiter())
    186         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    187             "strokeMiter:%g ", SkScalarToFloat(strokeMiter));
    188     unsigned flags = buffer.readU16();
    189     if (flags != defaultPaint.getFlags())
    190         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    191             "flags:0x%x ", flags);
    192     int align = buffer.readU8();
    193     if (align != defaultPaint.getTextAlign())
    194         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    195             "align:0x%x ", align);
    196     int strokeCap = buffer.readU8();
    197     if (strokeCap != defaultPaint.getStrokeCap())
    198         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    199             "strokeCap:0x%x ", strokeCap);
    200     int strokeJoin = buffer.readU8();
    201     if (strokeJoin != defaultPaint.getStrokeJoin())
    202         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    203             "align:0x%x ", strokeJoin);
    204     int style = buffer.readU8();
    205     if (style != defaultPaint.getStyle())
    206         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    207             "style:0x%x ", style);
    208     int textEncoding = buffer.readU8();
    209     if (textEncoding != defaultPaint.getTextEncoding())
    210         bufferPtr += snprintf(bufferPtr, DUMP_BUFFER_SIZE - (bufferPtr - pBuffer),
    211             "textEncoding:0x%x ", textEncoding);
    212     SkDebugf("%s\n", pBuffer);
    213 }
    214 #endif
    215 
    216 SkFlatRegion* SkFlatRegion::Flatten(SkChunkAlloc* heap, const SkRegion& region, int index) {
    217     uint32_t size = region.flatten(NULL);
    218     SkFlatRegion* result = (SkFlatRegion*) INHERITED::Alloc(heap, size, index);
    219     region.flatten(&result->fRegionData);
    220     return result;
    221 }
    222 
    223 ///////////////////////////////////////////////////////////////////////////////
    224 
    225 SkRefCntPlayback::SkRefCntPlayback() : fCount(0), fArray(NULL) {}
    226 
    227 SkRefCntPlayback::~SkRefCntPlayback() {
    228     this->reset(NULL);
    229 }
    230 
    231 void SkRefCntPlayback::reset(const SkRefCntSet* rec) {
    232     for (int i = 0; i < fCount; i++) {
    233         SkASSERT(fArray[i]);
    234         fArray[i]->unref();
    235     }
    236     SkDELETE_ARRAY(fArray);
    237 
    238     if (rec) {
    239         fCount = rec->count();
    240         fArray = SkNEW_ARRAY(SkRefCnt*, fCount);
    241         rec->copyToArray(fArray);
    242         for (int i = 0; i < fCount; i++) {
    243             fArray[i]->ref();
    244         }
    245     } else {
    246         fCount = 0;
    247         fArray = NULL;
    248     }
    249 }
    250 
    251 void SkRefCntPlayback::setCount(int count) {
    252     this->reset(NULL);
    253 
    254     fCount = count;
    255     fArray = SkNEW_ARRAY(SkRefCnt*, count);
    256     sk_bzero(fArray, count * sizeof(SkRefCnt*));
    257 }
    258 
    259 SkRefCnt* SkRefCntPlayback::set(int index, SkRefCnt* obj) {
    260     SkASSERT((unsigned)index < (unsigned)fCount);
    261     SkRefCnt_SafeAssign(fArray[index], obj);
    262     return obj;
    263 }
    264 
    265