1 | /* |
2 | * Copyright 2016 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 | #include "include/core/SkMatrix.h" |
9 | #include "include/core/SkPictureRecorder.h" |
10 | #include "src/core/SkPictureData.h" |
11 | #include "src/core/SkPicturePlayback.h" |
12 | #include "src/core/SkPictureRecord.h" |
13 | #include "src/core/SkRecordDraw.h" |
14 | #include "src/core/SkRecordedDrawable.h" |
15 | |
16 | void SkRecordedDrawable::onDraw(SkCanvas* canvas) { |
17 | SkDrawable* const* drawables = nullptr; |
18 | int drawableCount = 0; |
19 | if (fDrawableList) { |
20 | drawables = fDrawableList->begin(); |
21 | drawableCount = fDrawableList->count(); |
22 | } |
23 | SkRecordDraw(*fRecord, canvas, nullptr, drawables, drawableCount, fBBH.get(), nullptr); |
24 | } |
25 | |
26 | SkPicture* SkRecordedDrawable::onNewPictureSnapshot() { |
27 | // TODO: should we plumb-down the BBHFactory and recordFlags from our host |
28 | // PictureRecorder? |
29 | std::unique_ptr<SkBigPicture::SnapshotArray> pictList{ |
30 | fDrawableList ? fDrawableList->newDrawableSnapshot() : nullptr |
31 | }; |
32 | |
33 | size_t subPictureBytes = 0; |
34 | for (int i = 0; pictList && i < pictList->count(); i++) { |
35 | subPictureBytes += pictList->begin()[i]->approximateBytesUsed(); |
36 | } |
37 | return new SkBigPicture(fBounds, fRecord, std::move(pictList), fBBH, subPictureBytes); |
38 | } |
39 | |
40 | void SkRecordedDrawable::flatten(SkWriteBuffer& buffer) const { |
41 | // Write the bounds. |
42 | buffer.writeRect(fBounds); |
43 | |
44 | // Create an SkPictureRecord to record the draw commands. |
45 | SkPictInfo info; |
46 | SkPictureRecord pictureRecord(SkISize::Make(fBounds.width(), fBounds.height()), 0); |
47 | |
48 | // If the query contains the whole picture, don't bother with the bounding box hierarchy. |
49 | SkBBoxHierarchy* bbh; |
50 | if (pictureRecord.getLocalClipBounds().contains(fBounds)) { |
51 | bbh = nullptr; |
52 | } else { |
53 | bbh = fBBH.get(); |
54 | } |
55 | |
56 | // Record the draw commands. |
57 | pictureRecord.beginRecording(); |
58 | SkRecordDraw(*fRecord, &pictureRecord, nullptr, fDrawableList->begin(), fDrawableList->count(), |
59 | bbh, nullptr); |
60 | pictureRecord.endRecording(); |
61 | |
62 | // Flatten the recorded commands and drawables. |
63 | SkPictureData pictureData(pictureRecord, info); |
64 | pictureData.flatten(buffer); |
65 | } |
66 | |
67 | sk_sp<SkFlattenable> SkRecordedDrawable::CreateProc(SkReadBuffer& buffer) { |
68 | // Read the bounds. |
69 | SkRect bounds; |
70 | buffer.readRect(&bounds); |
71 | |
72 | // Unflatten into a SkPictureData. |
73 | SkPictInfo info; |
74 | info.setVersion(buffer.getVersion()); |
75 | info.fCullRect = bounds; |
76 | std::unique_ptr<SkPictureData> pictureData(SkPictureData::CreateFromBuffer(buffer, info)); |
77 | if (!pictureData) { |
78 | return nullptr; |
79 | } |
80 | |
81 | // Create a drawable. |
82 | SkPicturePlayback playback(pictureData.get()); |
83 | SkPictureRecorder recorder; |
84 | playback.draw(recorder.beginRecording(bounds), nullptr, &buffer); |
85 | return recorder.finishRecordingAsDrawable(); |
86 | } |
87 | |