const SkTDArray<bool>& deletedCommands) {
// Mimics SkPicturePlayback::CreateFromStream
SkAutoTDelete<SkTimedPicturePlayback> playback(SkNEW_ARGS(SkTimedPicturePlayback,
- (deletedCommands)));
- if (!playback->parseStream(stream, info, proc)) {
+ (deletedCommands, info)));
+ if (!playback->parseStream(stream, proc)) {
return NULL; // we're invalid
}
return playback.detach();
}
- SkTimedPicturePlayback(const SkTDArray<bool>& deletedCommands)
- : INHERITED()
+ SkTimedPicturePlayback(const SkTDArray<bool>& deletedCommands, const SkPictInfo& info)
+ : INHERITED(info)
, fSkipCommands(deletedCommands)
, fTot(0.0)
, fCurCommand(0) {
#endif
private:
- // SkPicturePlayback::parseStream is protected, so it can be
- // called here, but not by our static factory function. This
- // allows the factory function to call it.
- bool parseStream(SkStream* stream, const SkPictInfo& info,
- SkPicture::InstallPixelRefProc proc) {
- return this->INHERITED::parseStream(stream, info, proc);
- }
-
typedef SkPicturePlayback INHERITED;
};
SkReadBuffer(SkStream* stream);
virtual ~SkReadBuffer();
+ /** Return the version of the serialized picture this buffer holds, or 0 if unset. */
+ int pictureVersion() const { return fPictureVersion; }
+
+ /** This may be called at most once; most clients of SkReadBuffer should not mess with it. */
+ void setPictureVersion(int version) {
+ SkASSERT(0 == fPictureVersion);
+ fPictureVersion = version;
+ }
+
enum Flags {
kCrossProcess_Flag = 1 << 0,
kScalarIsFloat_Flag = 1 << 1,
bool readArray(void* value, size_t size, size_t elementSize);
uint32_t fFlags;
+ int fPictureVersion;
void* fMemoryPtr;
if (src.fPlayback) {
fPlayback = SkNEW_ARGS(SkPicturePlayback, (*src.fPlayback));
} else if (src.fRecord) {
+ SkPictInfo info;
+ this->createHeader(&info);
// here we do a fake src.endRecording()
- fPlayback = SkNEW_ARGS(SkPicturePlayback, (*src.fRecord));
+ fPlayback = SkNEW_ARGS(SkPicturePlayback, (*src.fRecord, info));
} else {
fPlayback = NULL;
}
void SkPicture::clone(SkPicture* pictures, int count) const {
SkPictCopyInfo copyInfo;
+ SkPictInfo info;
+ this->createHeader(&info);
for (int i = 0; i < count; i++) {
SkPicture* clone = &pictures[i];
clone->fPlayback = SkNEW_ARGS(SkPicturePlayback, (*fPlayback, ©Info));
} else if (fRecord) {
// here we do a fake src.endRecording()
- clone->fPlayback = SkNEW_ARGS(SkPicturePlayback, (*fRecord, true));
+ clone->fPlayback = SkNEW_ARGS(SkPicturePlayback, (*fRecord, info, true));
} else {
clone->fPlayback = NULL;
}
if (NULL == fPlayback) {
if (NULL != fRecord) {
fRecord->endRecording();
- fPlayback = SkNEW_ARGS(SkPicturePlayback, (*fRecord));
+ SkPictInfo info;
+ this->createHeader(&info);
+ fPlayback = SkNEW_ARGS(SkPicturePlayback, (*fRecord, info));
SkSafeSetNull(fRecord);
}
}
SkPicturePlayback* playback;
// Check to see if there is a playback to recreate.
if (buffer.readBool()) {
- playback = SkPicturePlayback::CreateFromBuffer(buffer);
+ playback = SkPicturePlayback::CreateFromBuffer(buffer, info);
if (NULL == playback) {
return NULL;
}
void SkPicture::serialize(SkWStream* stream, EncodeBitmap encoder) const {
SkPicturePlayback* playback = fPlayback;
+ SkPictInfo info;
+ this->createHeader(&info);
if (NULL == playback && fRecord) {
- playback = SkNEW_ARGS(SkPicturePlayback, (*fRecord));
+ playback = SkNEW_ARGS(SkPicturePlayback, (*fRecord, info));
}
- SkPictInfo header;
- this->createHeader(&header);
- stream->write(&header, sizeof(header));
+ stream->write(&info, sizeof(info));
if (playback) {
stream->writeBool(true);
playback->serialize(stream, encoder);
void SkPicture::flatten(SkWriteBuffer& buffer) const {
SkPicturePlayback* playback = fPlayback;
+ SkPictInfo info;
+ this->createHeader(&info);
if (NULL == playback && fRecord) {
- playback = SkNEW_ARGS(SkPicturePlayback, (*fRecord));
+ playback = SkNEW_ARGS(SkPicturePlayback, (*fRecord, info));
}
- SkPictInfo header;
- this->createHeader(&header);
- buffer.writeByteArray(&header, sizeof(header));
+ buffer.writeByteArray(&info, sizeof(info));
if (playback) {
buffer.writeBool(true);
playback->flatten(buffer);
*/
#define SPEW_CLIP_SKIPPINGx
-SkPicturePlayback::SkPicturePlayback() {
+SkPicturePlayback::SkPicturePlayback(const SkPictInfo& info) : fInfo(info) {
this->init();
}
-SkPicturePlayback::SkPicturePlayback(const SkPictureRecord& record, bool deepCopy) {
+SkPicturePlayback::SkPicturePlayback(const SkPictureRecord& record,
+ const SkPictInfo& info,
+ bool deepCopy)
+ : fInfo(info) {
#ifdef SK_DEBUG_SIZE
size_t overallBytes, bitmapBytes, matricesBytes,
paintBytes, pathBytes, pictureBytes, regionBytes;
paint.getImageFilter();
}
-SkPicturePlayback::SkPicturePlayback(const SkPicturePlayback& src, SkPictCopyInfo* deepCopyInfo) {
+SkPicturePlayback::SkPicturePlayback(const SkPicturePlayback& src, SkPictCopyInfo* deepCopyInfo)
+ : fInfo(src.fInfo) {
this->init();
fBitmapHeap.reset(SkSafeRef(src.fBitmapHeap.get()));
return rbMask;
}
-bool SkPicturePlayback::parseStreamTag(SkStream* stream, const SkPictInfo& info, uint32_t tag,
- size_t size, SkPicture::InstallPixelRefProc proc) {
+bool SkPicturePlayback::parseStreamTag(SkStream* stream,
+ uint32_t tag,
+ size_t size,
+ SkPicture::InstallPixelRefProc proc) {
/*
* By the time we encounter BUFFER_SIZE_TAG, we need to have already seen
* its dependents: FACTORY_TAG and TYPEFACE_TAG. These two are not required
// Remove this code when v21 and below are no longer supported. At the
// same time add a new 'count' variable and use it rather then reusing 'size'.
#ifndef DISABLE_V21_COMPATIBILITY_CODE
- if (info.fVersion >= 22) {
+ if (fInfo.fVersion >= 22) {
// in v22 this tag's size represents the size of the chunk in bytes
// and the number of factory strings is written out separately
#endif
}
SkReadBuffer buffer(storage.get(), size);
- buffer.setFlags(pictInfoFlagsToReadBufferFlags(info.fFlags));
+ buffer.setFlags(pictInfoFlagsToReadBufferFlags(fInfo.fFlags));
+ buffer.setPictureVersion(fInfo.fVersion);
fFactoryPlayback->setupBuffer(buffer);
fTFPlayback.setupBuffer(buffer);
SkPicturePlayback* SkPicturePlayback::CreateFromStream(SkStream* stream,
const SkPictInfo& info,
SkPicture::InstallPixelRefProc proc) {
- SkAutoTDelete<SkPicturePlayback> playback(SkNEW(SkPicturePlayback));
+ SkAutoTDelete<SkPicturePlayback> playback(SkNEW_ARGS(SkPicturePlayback, (info)));
- if (!playback->parseStream(stream, info, proc)) {
+ if (!playback->parseStream(stream, proc)) {
return NULL;
}
return playback.detach();
}
-SkPicturePlayback* SkPicturePlayback::CreateFromBuffer(SkReadBuffer& buffer) {
- SkAutoTDelete<SkPicturePlayback> playback(SkNEW(SkPicturePlayback));
+SkPicturePlayback* SkPicturePlayback::CreateFromBuffer(SkReadBuffer& buffer,
+ const SkPictInfo& info) {
+ SkAutoTDelete<SkPicturePlayback> playback(SkNEW_ARGS(SkPicturePlayback, (info)));
+ buffer.setPictureVersion(info.fVersion);
if (!playback->parseBuffer(buffer)) {
return NULL;
return playback.detach();
}
-bool SkPicturePlayback::parseStream(SkStream* stream, const SkPictInfo& info,
+bool SkPicturePlayback::parseStream(SkStream* stream,
SkPicture::InstallPixelRefProc proc) {
for (;;) {
uint32_t tag = stream->readU32();
}
uint32_t size = stream->readU32();
- if (!this->parseStreamTag(stream, info, tag, size, proc)) {
+ if (!this->parseStreamTag(stream, tag, size, proc)) {
return false; // we're invalid
}
}
class SkPicturePlayback {
public:
- SkPicturePlayback();
SkPicturePlayback(const SkPicturePlayback& src, SkPictCopyInfo* deepCopyInfo = NULL);
- explicit SkPicturePlayback(const SkPictureRecord& record, bool deepCopy = false);
- static SkPicturePlayback* CreateFromStream(SkStream*, const SkPictInfo&,
+ SkPicturePlayback(const SkPictureRecord& record, const SkPictInfo&, bool deepCopy = false);
+ static SkPicturePlayback* CreateFromStream(SkStream*,
+ const SkPictInfo&,
SkPicture::InstallPixelRefProc);
- static SkPicturePlayback* CreateFromBuffer(SkReadBuffer&);
+ static SkPicturePlayback* CreateFromBuffer(SkReadBuffer&, const SkPictInfo&);
virtual ~SkPicturePlayback();
void resetOpID() { fCurOffset = 0; }
protected:
- bool parseStream(SkStream*, const SkPictInfo&,
- SkPicture::InstallPixelRefProc);
+ explicit SkPicturePlayback(const SkPictInfo& info);
+
+ bool parseStream(SkStream*, SkPicture::InstallPixelRefProc);
bool parseBuffer(SkReadBuffer& buffer);
#ifdef SK_DEVELOPER
virtual bool preDraw(int opIndex, int type);
#endif
private: // these help us with reading/writing
- bool parseStreamTag(SkStream*, const SkPictInfo&, uint32_t tag, size_t size,
- SkPicture::InstallPixelRefProc);
+ bool parseStreamTag(SkStream*, uint32_t tag, size_t size, SkPicture::InstallPixelRefProc);
bool parseBufferTag(SkReadBuffer&, uint32_t tag, size_t size);
void flattenToBuffer(SkWriteBuffer&) const;
// The offset of the current operation when within the draw method
size_t fCurOffset;
+ const SkPictInfo fInfo;
+
#ifdef SK_BUILD_FOR_ANDROID
SkMutex fDrawMutex;
bool fAbortCurrentPlayback;
SkReadBuffer::SkReadBuffer() {
fFlags = default_flags();
+ fPictureVersion = 0;
fMemoryPtr = NULL;
fBitmapStorage = NULL;
SkReadBuffer::SkReadBuffer(const void* data, size_t size) {
fFlags = default_flags();
+ fPictureVersion = 0;
fReader.setMemory(data, size);
fMemoryPtr = NULL;
SkReadBuffer::SkReadBuffer(SkStream* stream) {
fFlags = default_flags();
+ fPictureVersion = 0;
const size_t length = stream->getLength();
fMemoryPtr = sk_malloc_throw(length);
stream->read(fMemoryPtr, length);