blob: 149cf7cc02c01263e76943e26c4080099d8d347d [file] [log] [blame]
epoger@google.comec3ed6a2011-07-28 14:26:00 +00001
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 */
reed@android.com8a1c16f2008-12-17 15:59:43 +00008#include "SkPictureFlat.h"
9
junov@chromium.orgef760602012-06-27 20:03:16 +000010#include "SkChecksum.h"
reed@android.com8a1c16f2008-12-17 15:59:43 +000011#include "SkColorFilter.h"
12#include "SkDrawLooper.h"
13#include "SkMaskFilter.h"
14#include "SkRasterizer.h"
15#include "SkShader.h"
16#include "SkTypeface.h"
17#include "SkXfermode.h"
18
reed@android.com8a1c16f2008-12-17 15:59:43 +000019///////////////////////////////////////////////////////////////////////////////
20
djsollen@google.com21830d92012-08-07 19:49:41 +000021SkTypefacePlayback::SkTypefacePlayback() : fCount(0), fArray(NULL) {}
reed@android.com8a1c16f2008-12-17 15:59:43 +000022
djsollen@google.com21830d92012-08-07 19:49:41 +000023SkTypefacePlayback::~SkTypefacePlayback() {
reed@android.com8a1c16f2008-12-17 15:59:43 +000024 this->reset(NULL);
25}
26
djsollen@google.com21830d92012-08-07 19:49:41 +000027void SkTypefacePlayback::reset(const SkRefCntSet* rec) {
reed@android.com8a1c16f2008-12-17 15:59:43 +000028 for (int i = 0; i < fCount; i++) {
29 SkASSERT(fArray[i]);
30 fArray[i]->unref();
31 }
32 SkDELETE_ARRAY(fArray);
rmistry@google.comfbfcd562012-08-23 18:09:54 +000033
scroggo@google.com15543602012-08-02 18:49:49 +000034 if (rec!= NULL && rec->count() > 0) {
reed@android.com8a1c16f2008-12-17 15:59:43 +000035 fCount = rec->count();
36 fArray = SkNEW_ARRAY(SkRefCnt*, fCount);
mike@reedtribe.orge9e08cc2011-04-29 01:44:52 +000037 rec->copyToArray(fArray);
reed@android.com8a1c16f2008-12-17 15:59:43 +000038 for (int i = 0; i < fCount; i++) {
39 fArray[i]->ref();
40 }
41 } else {
42 fCount = 0;
43 fArray = NULL;
44 }
45}
46
djsollen@google.com21830d92012-08-07 19:49:41 +000047void SkTypefacePlayback::setCount(int count) {
reed@android.com8a1c16f2008-12-17 15:59:43 +000048 this->reset(NULL);
rmistry@google.comfbfcd562012-08-23 18:09:54 +000049
reed@android.com8a1c16f2008-12-17 15:59:43 +000050 fCount = count;
51 fArray = SkNEW_ARRAY(SkRefCnt*, count);
reed@android.com4516f472009-06-29 16:25:36 +000052 sk_bzero(fArray, count * sizeof(SkRefCnt*));
reed@android.com8a1c16f2008-12-17 15:59:43 +000053}
54
djsollen@google.com21830d92012-08-07 19:49:41 +000055SkRefCnt* SkTypefacePlayback::set(int index, SkRefCnt* obj) {
reed@android.com8a1c16f2008-12-17 15:59:43 +000056 SkASSERT((unsigned)index < (unsigned)fCount);
57 SkRefCnt_SafeAssign(fArray[index], obj);
58 return obj;
59}
60
djsollen@google.comd2700ee2012-05-30 16:54:13 +000061///////////////////////////////////////////////////////////////////////////////
62
scroggo@google.com15543602012-08-02 18:49:49 +000063SkFlatController::SkFlatController()
djsollen@google.com21830d92012-08-07 19:49:41 +000064: fBitmapHeap(NULL)
scroggo@google.com15543602012-08-02 18:49:49 +000065, fTypefaceSet(NULL)
scroggo@google.com15543602012-08-02 18:49:49 +000066, fTypefacePlayback(NULL)
scroggo@google.com664fab12012-08-14 19:22:05 +000067, fFactorySet(NULL)
68, fWriteBufferFlags(0) {}
scroggo@google.com15543602012-08-02 18:49:49 +000069
70SkFlatController::~SkFlatController() {
djsollen@google.com21830d92012-08-07 19:49:41 +000071 SkSafeUnref(fBitmapHeap);
scroggo@google.com15543602012-08-02 18:49:49 +000072 SkSafeUnref(fTypefaceSet);
73 SkSafeUnref(fFactorySet);
74}
75
djsollen@google.com21830d92012-08-07 19:49:41 +000076void SkFlatController::setBitmapHeap(SkBitmapHeap* heap) {
77 SkRefCnt_SafeAssign(fBitmapHeap, heap);
scroggo@google.com15543602012-08-02 18:49:49 +000078}
79
80void SkFlatController::setTypefaceSet(SkRefCntSet *set) {
81 SkRefCnt_SafeAssign(fTypefaceSet, set);
82}
83
scroggo@google.com15543602012-08-02 18:49:49 +000084void SkFlatController::setTypefacePlayback(SkTypefacePlayback* playback) {
85 fTypefacePlayback = playback;
86}
87
88SkNamedFactorySet* SkFlatController::setNamedFactorySet(SkNamedFactorySet* set) {
89 SkRefCnt_SafeAssign(fFactorySet, set);
90 return set;
91}
92
93///////////////////////////////////////////////////////////////////////////////
94
mtklein@google.com9e3074e2013-08-20 16:48:47 +000095SkFlatData* SkFlatData::Create(SkFlatController* controller,
96 const void* obj,
97 int index,
98 void (*flattenProc)(SkOrderedWriteBuffer&, const void*)) {
djsollen@google.comd2700ee2012-05-30 16:54:13 +000099 // a buffer of 256 bytes should be sufficient for most paints, regions,
100 // and matrices.
101 intptr_t storage[256];
102 SkOrderedWriteBuffer buffer(256, storage, sizeof(storage));
scroggo@google.com15543602012-08-02 18:49:49 +0000103
djsollen@google.com21830d92012-08-07 19:49:41 +0000104 buffer.setBitmapHeap(controller->getBitmapHeap());
scroggo@google.com15543602012-08-02 18:49:49 +0000105 buffer.setTypefaceRecorder(controller->getTypefaceSet());
106 buffer.setNamedFactoryRecorder(controller->getNamedFactorySet());
scroggo@google.com664fab12012-08-14 19:22:05 +0000107 buffer.setFlags(controller->getWriteBufferFlags());
rmistry@google.comfbfcd562012-08-23 18:09:54 +0000108
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000109 flattenProc(buffer, obj);
110 uint32_t size = buffer.size();
reed@google.come2589ae2012-07-10 19:38:01 +0000111 SkASSERT(SkIsAlign4(size));
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000112
mtklein@google.com9e3074e2013-08-20 16:48:47 +0000113 // Allocate enough memory to hold SkFlatData struct and the flat data itself.
114 size_t allocSize = sizeof(SkFlatData) + size;
scroggo@google.com4dffc592012-07-17 16:49:40 +0000115 SkFlatData* result = (SkFlatData*) controller->allocThrow(allocSize);
reed@google.come2589ae2012-07-10 19:38:01 +0000116
mtklein@google.com9e3074e2013-08-20 16:48:47 +0000117 // Put the serialized contents into the data section of the new allocation.
djsollen@google.comc73dd5c2012-08-07 15:54:32 +0000118 buffer.writeToMemory(result->data());
mtklein@google.com9e3074e2013-08-20 16:48:47 +0000119 // Stamp the index, size and checksum in the header.
120 result->stampHeader(index, size);
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000121 return result;
122}
123
124void SkFlatData::unflatten(void* result,
125 void (*unflattenProc)(SkOrderedReadBuffer&, void*),
djsollen@google.com21830d92012-08-07 19:49:41 +0000126 SkBitmapHeap* bitmapHeap,
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000127 SkTypefacePlayback* facePlayback) const {
128
reed@google.come2589ae2012-07-10 19:38:01 +0000129 SkOrderedReadBuffer buffer(this->data(), fFlatSize);
djsollen@google.com21830d92012-08-07 19:49:41 +0000130
131 if (bitmapHeap) {
132 buffer.setBitmapStorage(bitmapHeap);
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000133 }
134 if (facePlayback) {
135 facePlayback->setupBuffer(buffer);
136 }
djsollen@google.com21830d92012-08-07 19:49:41 +0000137
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000138 unflattenProc(buffer, result);
reed@google.come2589ae2012-07-10 19:38:01 +0000139 SkASSERT(fFlatSize == (int32_t)buffer.offset());
djsollen@google.comd2700ee2012-05-30 16:54:13 +0000140}