| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2011 Google Inc. | 2 * Copyright 2011 Google Inc. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
| 5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
| 6 */ | 6 */ |
| 7 #include <new> | 7 #include <new> |
| 8 #include "SkPictureData.h" | 8 #include "SkPictureData.h" |
| 9 #include "SkPictureRecord.h" | 9 #include "SkPictureRecord.h" |
| 10 #include "SkReadBuffer.h" | 10 #include "SkReadBuffer.h" |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 73 fImageCount = imgs.count(); | 73 fImageCount = imgs.count(); |
| 74 if (fImageCount > 0) { | 74 if (fImageCount > 0) { |
| 75 fImageRefs = new const SkImage* [fImageCount]; | 75 fImageRefs = new const SkImage* [fImageCount]; |
| 76 for (int i = 0; i < fImageCount; ++i) { | 76 for (int i = 0; i < fImageCount; ++i) { |
| 77 fImageRefs[i] = SkRef(imgs[i]); | 77 fImageRefs[i] = SkRef(imgs[i]); |
| 78 } | 78 } |
| 79 } | 79 } |
| 80 } | 80 } |
| 81 | 81 |
| 82 void SkPictureData::init() { | 82 void SkPictureData::init() { |
| 83 fPictureRefs = NULL; | 83 fPictureRefs = nullptr; |
| 84 fPictureCount = 0; | 84 fPictureCount = 0; |
| 85 fTextBlobRefs = NULL; | 85 fTextBlobRefs = nullptr; |
| 86 fTextBlobCount = 0; | 86 fTextBlobCount = 0; |
| 87 fImageRefs = NULL; | 87 fImageRefs = nullptr; |
| 88 fImageCount = 0; | 88 fImageCount = 0; |
| 89 fOpData = NULL; | 89 fOpData = nullptr; |
| 90 fFactoryPlayback = NULL; | 90 fFactoryPlayback = nullptr; |
| 91 } | 91 } |
| 92 | 92 |
| 93 SkPictureData::~SkPictureData() { | 93 SkPictureData::~SkPictureData() { |
| 94 SkSafeUnref(fOpData); | 94 SkSafeUnref(fOpData); |
| 95 | 95 |
| 96 for (int i = 0; i < fPictureCount; i++) { | 96 for (int i = 0; i < fPictureCount; i++) { |
| 97 fPictureRefs[i]->unref(); | 97 fPictureRefs[i]->unref(); |
| 98 } | 98 } |
| 99 delete[] fPictureRefs; | 99 delete[] fPictureRefs; |
| 100 | 100 |
| (...skipping 25 matching lines...) Expand all Loading... |
| 126 /////////////////////////////////////////////////////////////////////////////// | 126 /////////////////////////////////////////////////////////////////////////////// |
| 127 /////////////////////////////////////////////////////////////////////////////// | 127 /////////////////////////////////////////////////////////////////////////////// |
| 128 | 128 |
| 129 #include "SkStream.h" | 129 #include "SkStream.h" |
| 130 | 130 |
| 131 static size_t compute_chunk_size(SkFlattenable::Factory* array, int count) { | 131 static size_t compute_chunk_size(SkFlattenable::Factory* array, int count) { |
| 132 size_t size = 4; // for 'count' | 132 size_t size = 4; // for 'count' |
| 133 | 133 |
| 134 for (int i = 0; i < count; i++) { | 134 for (int i = 0; i < count; i++) { |
| 135 const char* name = SkFlattenable::FactoryToName(array[i]); | 135 const char* name = SkFlattenable::FactoryToName(array[i]); |
| 136 if (NULL == name || 0 == *name) { | 136 if (nullptr == name || 0 == *name) { |
| 137 size += SkWStream::SizeOfPackedUInt(0); | 137 size += SkWStream::SizeOfPackedUInt(0); |
| 138 } else { | 138 } else { |
| 139 size_t len = strlen(name); | 139 size_t len = strlen(name); |
| 140 size += SkWStream::SizeOfPackedUInt(len); | 140 size += SkWStream::SizeOfPackedUInt(len); |
| 141 size += len; | 141 size += len; |
| 142 } | 142 } |
| 143 } | 143 } |
| 144 | 144 |
| 145 return size; | 145 return size; |
| 146 } | 146 } |
| (...skipping 17 matching lines...) Expand all Loading... |
| 164 | 164 |
| 165 size_t size = compute_chunk_size(array, count); | 165 size_t size = compute_chunk_size(array, count); |
| 166 | 166 |
| 167 // TODO: write_tag_size should really take a size_t | 167 // TODO: write_tag_size should really take a size_t |
| 168 write_tag_size(stream, SK_PICT_FACTORY_TAG, (uint32_t) size); | 168 write_tag_size(stream, SK_PICT_FACTORY_TAG, (uint32_t) size); |
| 169 SkDEBUGCODE(size_t start = stream->bytesWritten()); | 169 SkDEBUGCODE(size_t start = stream->bytesWritten()); |
| 170 stream->write32(count); | 170 stream->write32(count); |
| 171 | 171 |
| 172 for (int i = 0; i < count; i++) { | 172 for (int i = 0; i < count; i++) { |
| 173 const char* name = SkFlattenable::FactoryToName(array[i]); | 173 const char* name = SkFlattenable::FactoryToName(array[i]); |
| 174 if (NULL == name || 0 == *name) { | 174 if (nullptr == name || 0 == *name) { |
| 175 stream->writePackedUInt(0); | 175 stream->writePackedUInt(0); |
| 176 } else { | 176 } else { |
| 177 size_t len = strlen(name); | 177 size_t len = strlen(name); |
| 178 stream->writePackedUInt(len); | 178 stream->writePackedUInt(len); |
| 179 stream->write(name, len); | 179 stream->write(name, len); |
| 180 } | 180 } |
| 181 } | 181 } |
| 182 | 182 |
| 183 SkASSERT(size == (stream->bytesWritten() - start)); | 183 SkASSERT(size == (stream->bytesWritten() - start)); |
| 184 } | 184 } |
| (...skipping 163 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 348 * but if they are present, they need to have been seen before the buffer. | 348 * but if they are present, they need to have been seen before the buffer. |
| 349 * | 349 * |
| 350 * We assert that if/when we see either of these, that we have not yet seen | 350 * We assert that if/when we see either of these, that we have not yet seen |
| 351 * the buffer tag, because if we have, then its too-late to deal with the | 351 * the buffer tag, because if we have, then its too-late to deal with the |
| 352 * factories or typefaces. | 352 * factories or typefaces. |
| 353 */ | 353 */ |
| 354 SkDEBUGCODE(bool haveBuffer = false;) | 354 SkDEBUGCODE(bool haveBuffer = false;) |
| 355 | 355 |
| 356 switch (tag) { | 356 switch (tag) { |
| 357 case SK_PICT_READER_TAG: | 357 case SK_PICT_READER_TAG: |
| 358 SkASSERT(NULL == fOpData); | 358 SkASSERT(nullptr == fOpData); |
| 359 fOpData = SkData::NewFromStream(stream, size); | 359 fOpData = SkData::NewFromStream(stream, size); |
| 360 if (!fOpData) { | 360 if (!fOpData) { |
| 361 return false; | 361 return false; |
| 362 } | 362 } |
| 363 break; | 363 break; |
| 364 case SK_PICT_FACTORY_TAG: { | 364 case SK_PICT_FACTORY_TAG: { |
| 365 SkASSERT(!haveBuffer); | 365 SkASSERT(!haveBuffer); |
| 366 size = stream->readU32(); | 366 size = stream->readU32(); |
| 367 fFactoryPlayback = new SkFactoryPlayback(size); | 367 fFactoryPlayback = new SkFactoryPlayback(size); |
| 368 for (size_t i = 0; i < size; i++) { | 368 for (size_t i = 0; i < size; i++) { |
| (...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 436 } break; | 436 } break; |
| 437 } | 437 } |
| 438 return true; // success | 438 return true; // success |
| 439 } | 439 } |
| 440 | 440 |
| 441 static const SkImage* create_image_from_buffer(SkReadBuffer& buffer) { | 441 static const SkImage* create_image_from_buffer(SkReadBuffer& buffer) { |
| 442 int width = buffer.read32(); | 442 int width = buffer.read32(); |
| 443 int height = buffer.read32(); | 443 int height = buffer.read32(); |
| 444 if (width <= 0 || height <= 0) { // SkImage never has a zero dimension | 444 if (width <= 0 || height <= 0) { // SkImage never has a zero dimension |
| 445 buffer.validate(false); | 445 buffer.validate(false); |
| 446 return NULL; | 446 return nullptr; |
| 447 } | 447 } |
| 448 | 448 |
| 449 SkAutoTUnref<SkData> encoded(buffer.readByteArrayAsData()); | 449 SkAutoTUnref<SkData> encoded(buffer.readByteArrayAsData()); |
| 450 int originX = buffer.read32(); | 450 int originX = buffer.read32(); |
| 451 int originY = buffer.read32(); | 451 int originY = buffer.read32(); |
| 452 if (0 == encoded->size() || originX < 0 || originY < 0) { | 452 if (0 == encoded->size() || originX < 0 || originY < 0) { |
| 453 buffer.validate(false); | 453 buffer.validate(false); |
| 454 return NULL; | 454 return nullptr; |
| 455 } | 455 } |
| 456 | 456 |
| 457 const SkIRect subset = SkIRect::MakeXYWH(originX, originY, width, height); | 457 const SkIRect subset = SkIRect::MakeXYWH(originX, originY, width, height); |
| 458 return SkImage::NewFromEncoded(encoded, &subset); | 458 return SkImage::NewFromEncoded(encoded, &subset); |
| 459 } | 459 } |
| 460 | 460 |
| 461 // Need a shallow wrapper to return const SkPicture* to match the other factorie
s, | 461 // Need a shallow wrapper to return const SkPicture* to match the other factorie
s, |
| 462 // as SkPicture::CreateFromBuffer() returns SkPicture* | 462 // as SkPicture::CreateFromBuffer() returns SkPicture* |
| 463 static const SkPicture* create_picture_from_buffer(SkReadBuffer& buffer) { | 463 static const SkPicture* create_picture_from_buffer(SkReadBuffer& buffer) { |
| 464 return SkPicture::CreateFromBuffer(buffer); | 464 return SkPicture::CreateFromBuffer(buffer); |
| 465 } | 465 } |
| 466 | 466 |
| 467 template <typename T> | 467 template <typename T> |
| 468 bool new_array_from_buffer(SkReadBuffer& buffer, uint32_t inCount, | 468 bool new_array_from_buffer(SkReadBuffer& buffer, uint32_t inCount, |
| 469 const T*** array, int* outCount, const T* (*factory)(
SkReadBuffer&)) { | 469 const T*** array, int* outCount, const T* (*factory)(
SkReadBuffer&)) { |
| 470 if (!buffer.validate((0 == *outCount) && (NULL == *array))) { | 470 if (!buffer.validate((0 == *outCount) && (nullptr == *array))) { |
| 471 return false; | 471 return false; |
| 472 } | 472 } |
| 473 if (0 == inCount) { | 473 if (0 == inCount) { |
| 474 return true; | 474 return true; |
| 475 } | 475 } |
| 476 *outCount = inCount; | 476 *outCount = inCount; |
| 477 *array = new const T* [*outCount]; | 477 *array = new const T* [*outCount]; |
| 478 bool success = true; | 478 bool success = true; |
| 479 int i = 0; | 479 int i = 0; |
| 480 for (; i < *outCount; i++) { | 480 for (; i < *outCount; i++) { |
| 481 (*array)[i] = factory(buffer); | 481 (*array)[i] = factory(buffer); |
| 482 if (NULL == (*array)[i]) { | 482 if (nullptr == (*array)[i]) { |
| 483 success = false; | 483 success = false; |
| 484 break; | 484 break; |
| 485 } | 485 } |
| 486 } | 486 } |
| 487 if (!success) { | 487 if (!success) { |
| 488 // Delete all of the blobs that were already created (up to but excludin
g i): | 488 // Delete all of the blobs that were already created (up to but excludin
g i): |
| 489 for (int j = 0; j < i; j++) { | 489 for (int j = 0; j < i; j++) { |
| 490 (*array)[j]->unref(); | 490 (*array)[j]->unref(); |
| 491 } | 491 } |
| 492 // Delete the array | 492 // Delete the array |
| 493 delete[] * array; | 493 delete[] * array; |
| 494 *array = NULL; | 494 *array = nullptr; |
| 495 *outCount = 0; | 495 *outCount = 0; |
| 496 return false; | 496 return false; |
| 497 } | 497 } |
| 498 return true; | 498 return true; |
| 499 } | 499 } |
| 500 | 500 |
| 501 bool SkPictureData::parseBufferTag(SkReadBuffer& buffer, uint32_t tag, uint32_t
size) { | 501 bool SkPictureData::parseBufferTag(SkReadBuffer& buffer, uint32_t tag, uint32_t
size) { |
| 502 switch (tag) { | 502 switch (tag) { |
| 503 case SK_PICT_BITMAP_BUFFER_TAG: { | 503 case SK_PICT_BITMAP_BUFFER_TAG: { |
| 504 const int count = SkToInt(size); | 504 const int count = SkToInt(size); |
| (...skipping 30 matching lines...) Expand all Loading... |
| 535 break; | 535 break; |
| 536 case SK_PICT_IMAGE_BUFFER_TAG: | 536 case SK_PICT_IMAGE_BUFFER_TAG: |
| 537 if (!new_array_from_buffer(buffer, size, &fImageRefs, &fImageCount, | 537 if (!new_array_from_buffer(buffer, size, &fImageRefs, &fImageCount, |
| 538 create_image_from_buffer)) { | 538 create_image_from_buffer)) { |
| 539 return false; | 539 return false; |
| 540 } | 540 } |
| 541 break; | 541 break; |
| 542 case SK_PICT_READER_TAG: { | 542 case SK_PICT_READER_TAG: { |
| 543 SkAutoDataUnref data(SkData::NewUninitialized(size)); | 543 SkAutoDataUnref data(SkData::NewUninitialized(size)); |
| 544 if (!buffer.readByteArray(data->writable_data(), size) || | 544 if (!buffer.readByteArray(data->writable_data(), size) || |
| 545 !buffer.validate(NULL == fOpData)) { | 545 !buffer.validate(nullptr == fOpData)) { |
| 546 return false; | 546 return false; |
| 547 } | 547 } |
| 548 SkASSERT(NULL == fOpData); | 548 SkASSERT(nullptr == fOpData); |
| 549 fOpData = data.detach(); | 549 fOpData = data.detach(); |
| 550 } break; | 550 } break; |
| 551 case SK_PICT_PICTURE_TAG: | 551 case SK_PICT_PICTURE_TAG: |
| 552 if (!new_array_from_buffer(buffer, size, &fPictureRefs, &fPictureCou
nt, | 552 if (!new_array_from_buffer(buffer, size, &fPictureRefs, &fPictureCou
nt, |
| 553 create_picture_from_buffer)) { | 553 create_picture_from_buffer)) { |
| 554 return false; | 554 return false; |
| 555 } | 555 } |
| 556 break; | 556 break; |
| 557 default: | 557 default: |
| 558 // The tag was invalid. | 558 // The tag was invalid. |
| 559 return false; | 559 return false; |
| 560 } | 560 } |
| 561 return true; // success | 561 return true; // success |
| 562 } | 562 } |
| 563 | 563 |
| 564 SkPictureData* SkPictureData::CreateFromStream(SkStream* stream, | 564 SkPictureData* SkPictureData::CreateFromStream(SkStream* stream, |
| 565 const SkPictInfo& info, | 565 const SkPictInfo& info, |
| 566 SkPicture::InstallPixelRefProc pr
oc, | 566 SkPicture::InstallPixelRefProc pr
oc, |
| 567 SkTypefacePlayback* topLevelTFPla
yback) { | 567 SkTypefacePlayback* topLevelTFPla
yback) { |
| 568 SkAutoTDelete<SkPictureData> data(new SkPictureData(info)); | 568 SkAutoTDelete<SkPictureData> data(new SkPictureData(info)); |
| 569 if (!topLevelTFPlayback) { | 569 if (!topLevelTFPlayback) { |
| 570 topLevelTFPlayback = &data->fTFPlayback; | 570 topLevelTFPlayback = &data->fTFPlayback; |
| 571 } | 571 } |
| 572 | 572 |
| 573 if (!data->parseStream(stream, proc, topLevelTFPlayback)) { | 573 if (!data->parseStream(stream, proc, topLevelTFPlayback)) { |
| 574 return NULL; | 574 return nullptr; |
| 575 } | 575 } |
| 576 return data.detach(); | 576 return data.detach(); |
| 577 } | 577 } |
| 578 | 578 |
| 579 SkPictureData* SkPictureData::CreateFromBuffer(SkReadBuffer& buffer, | 579 SkPictureData* SkPictureData::CreateFromBuffer(SkReadBuffer& buffer, |
| 580 const SkPictInfo& info) { | 580 const SkPictInfo& info) { |
| 581 SkAutoTDelete<SkPictureData> data(new SkPictureData(info)); | 581 SkAutoTDelete<SkPictureData> data(new SkPictureData(info)); |
| 582 buffer.setVersion(info.fVersion); | 582 buffer.setVersion(info.fVersion); |
| 583 | 583 |
| 584 if (!data->parseBuffer(buffer)) { | 584 if (!data->parseBuffer(buffer)) { |
| 585 return NULL; | 585 return nullptr; |
| 586 } | 586 } |
| 587 return data.detach(); | 587 return data.detach(); |
| 588 } | 588 } |
| 589 | 589 |
| 590 bool SkPictureData::parseStream(SkStream* stream, | 590 bool SkPictureData::parseStream(SkStream* stream, |
| 591 SkPicture::InstallPixelRefProc proc, | 591 SkPicture::InstallPixelRefProc proc, |
| 592 SkTypefacePlayback* topLevelTFPlayback) { | 592 SkTypefacePlayback* topLevelTFPlayback) { |
| 593 for (;;) { | 593 for (;;) { |
| 594 uint32_t tag = stream->readU32(); | 594 uint32_t tag = stream->readU32(); |
| 595 if (SK_PICT_EOF_TAG == tag) { | 595 if (SK_PICT_EOF_TAG == tag) { |
| (...skipping 28 matching lines...) Expand all Loading... |
| 624 | 624 |
| 625 #if SK_SUPPORT_GPU | 625 #if SK_SUPPORT_GPU |
| 626 bool SkPictureData::suitableForGpuRasterization(GrContext* context, const char *
*reason, | 626 bool SkPictureData::suitableForGpuRasterization(GrContext* context, const char *
*reason, |
| 627 int sampleCount) const { | 627 int sampleCount) const { |
| 628 return fContentInfo.suitableForGpuRasterization(context, reason, sampleCount
); | 628 return fContentInfo.suitableForGpuRasterization(context, reason, sampleCount
); |
| 629 } | 629 } |
| 630 | 630 |
| 631 bool SkPictureData::suitableForGpuRasterization(GrContext* context, const char *
*reason, | 631 bool SkPictureData::suitableForGpuRasterization(GrContext* context, const char *
*reason, |
| 632 GrPixelConfig config, SkScalar d
pi) const { | 632 GrPixelConfig config, SkScalar d
pi) const { |
| 633 | 633 |
| 634 if (context != NULL) { | 634 if (context != nullptr) { |
| 635 return this->suitableForGpuRasterization(context, reason, | 635 return this->suitableForGpuRasterization(context, reason, |
| 636 context->getRecommendedSampleCo
unt(config, dpi)); | 636 context->getRecommendedSampleCo
unt(config, dpi)); |
| 637 } else { | 637 } else { |
| 638 return this->suitableForGpuRasterization(NULL, reason); | 638 return this->suitableForGpuRasterization(nullptr, reason); |
| 639 } | 639 } |
| 640 } | 640 } |
| 641 | 641 |
| 642 bool SkPictureData::suitableForLayerOptimization() const { | 642 bool SkPictureData::suitableForLayerOptimization() const { |
| 643 return fContentInfo.numLayers() > 0; | 643 return fContentInfo.numLayers() > 0; |
| 644 } | 644 } |
| 645 #endif | 645 #endif |
| 646 /////////////////////////////////////////////////////////////////////////////// | 646 /////////////////////////////////////////////////////////////////////////////// |
| 647 | 647 |
| 648 | 648 |
| OLD | NEW |