#Topic Picture
#Alias Pictures ##
#Alias Picture_Reference ##

#Class SkPicture

#Code
#Populate
##

Picture records drawing commands made to Canvas. The command stream may be
played in whole or in part at a later time.

Picture is an abstract class. Picture may be generated by Picture_Recorder
or Drawable, or from Picture previously saved to Data or Stream. 

Picture may contain any Canvas drawing command, as well as one or more
Canvas_Matrix or Canvas_Clip. Picture has a cull Rect, which is used as
a bounding box hint. To limit Picture bounds, use Canvas_Clip when
recording or drawing Picture.

# ------------------------------------------------------------------------------

#Class AbortCallback
#Line # utility to stop picture playback ##

#Code
    class AbortCallback {
    public:
        AbortCallback() {}
        virtual ~AbortCallback() {}
        virtual bool abort() = 0;
    };
##

AbortCallback is an abstract class. An implementation of AbortCallback may
passed as a parameter to SkPicture::playback, to stop it before all drawing
commands have been processed.

If AbortCallback::abort returns true, SkPicture::playback is interrupted.

# ------------------------------------------------------------------------------

#Method AbortCallback()
#In Constructors
#Line # defines default constructor ##
#Populate

#NoExample
##

#SeeAlso playback

#Method ##

# ------------------------------------------------------------------------------

#Method virtual ~AbortCallback()
#In Constructors
#Line # defines default destructor ##
#Populate

#NoExample
##

#SeeAlso playback

#Method ##

# ------------------------------------------------------------------------------

#Method virtual bool abort() = 0
#In Utility
#Line # aborts playback by callback ##
#Populate

#NoExample
##

#SeeAlso playback

#Method ##

#Example
#Description
JustOneDraw allows the black rectangle to draw but stops playback before the
white rectangle appears.
##
#Function
class JustOneDraw : public SkPicture::AbortCallback {
public:
    bool abort() override { return fCalls++ > 0; }
private:
    int fCalls = 0;
};
##

void draw(SkCanvas* canvas) {
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    JustOneDraw callback;
    picture->playback(canvas, &callback);
}

##

#Class AbortCallback ##

# ------------------------------------------------------------------------------

#Method static sk_sp<SkPicture> MakeFromStream(SkStream* stream,
                                           const SkDeserialProcs* procs = nullptr)
#In Constructors
#Line # constructs Picture from stream ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    SkDynamicMemoryWStream writableStream;
    picture->serialize(&writableStream);
    std::unique_ptr<SkStreamAsset> readableStream = writableStream.detachAsStream();
    sk_sp<SkPicture> copy = SkPicture::MakeFromStream(readableStream.get());
    copy->playback(canvas);
##

#SeeAlso MakeFromData SkPictureRecorder

#Method ##

# ------------------------------------------------------------------------------

#Method static sk_sp<SkPicture> MakeFromData(const SkData* data,
                                         const SkDeserialProcs* procs = nullptr)
#In Constructors
#Line # constructs Picture from data ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    SkDynamicMemoryWStream writableStream;
    picture->serialize(&writableStream);
    sk_sp<SkData> readableData = writableStream.detachAsData();
    sk_sp<SkPicture> copy = SkPicture::MakeFromData(readableData.get());
    copy->playback(canvas);
##

#SeeAlso MakeFromStream SkPictureRecorder

#Method ##

# ------------------------------------------------------------------------------

#Method static sk_sp<SkPicture> MakeFromData(const void* data, size_t size,
                                         const SkDeserialProcs* procs = nullptr)
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    SkDynamicMemoryWStream writableStream;
    picture->serialize(&writableStream);
    sk_sp<SkData> readableData = writableStream.detachAsData();
    sk_sp<SkPicture> copy = SkPicture::MakeFromData(readableData->data(), readableData->size());
    copy->playback(canvas);
##

#SeeAlso MakeFromStream SkPictureRecorder

#Method ##

# ------------------------------------------------------------------------------

#Method virtual void playback(SkCanvas* canvas, AbortCallback* callback = nullptr) const = 0
#In Action
#Line # replays drawing commands on canvas ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    picture->playback(canvas);
##

#SeeAlso SkCanvas::drawPicture

#Method ##

# ------------------------------------------------------------------------------

#Method virtual SkRect cullRect() const = 0
#In Property
#Line # returns bounds used to record Picture ##
#Populate

#Example
#Description
Picture recorded bounds are smaller than contents; contents outside recorded
bounds may be drawn, and are drawn in this example.
##
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({64, 64, 192, 192});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    picture->playback(canvas);
    paint.setBlendMode(SkBlendMode::kModulate);
    paint.setColor(0x40404040);
    canvas->drawRect(picture->cullRect(), paint);
##

#SeeAlso SkCanvas::clipRect

#Method ##

# ------------------------------------------------------------------------------

#Method uint32_t uniqueID() const
#In Property
#Line # returns identifier for Picture ##
#Populate

#Example
    SkPictureRecorder recorder;
    recorder.beginRecording({0, 0, 0, 0});
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    SkDebugf("empty picture id = %d\n", picture->uniqueID());
    sk_sp<SkPicture> placeholder = SkPicture::MakePlaceholder({0, 0, 0, 0});
    SkDebugf("placeholder id = %d\n", placeholder->uniqueID());
#StdOut
empty picture id = 1
placeholder id = 2
##
##

#SeeAlso SkRefCnt

#Method ##

# ------------------------------------------------------------------------------

#Method sk_sp<SkData> serialize(const SkSerialProcs* procs = nullptr) const
#In Utility
#Line # writes Picture to Data ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    sk_sp<SkData> readableData = picture->serialize();
    sk_sp<SkPicture> copy = SkPicture::MakeFromData(readableData->data(), readableData->size());
    copy->playback(canvas);
##

#SeeAlso MakeFromData SkData SkSerialProcs

#Method ##

# ------------------------------------------------------------------------------

#Method void serialize(SkWStream* stream, const SkSerialProcs* procs = nullptr) const
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    SkDynamicMemoryWStream writableStream;
    picture->serialize(&writableStream);
    sk_sp<SkData> readableData = writableStream.detachAsData();
    sk_sp<SkPicture> copy = SkPicture::MakeFromData(readableData->data(), readableData->size());
    copy->playback(canvas);
##

#SeeAlso MakeFromStream SkWStream SkSerialProcs

#Method ##

# ------------------------------------------------------------------------------

#Method static sk_sp<SkPicture> MakePlaceholder(SkRect cull)
#In Constructors
#Line # constructs placeholder with unique identifier ##
#Populate

#Example
#Function
class MyCanvas : public SkCanvas {
public:
    MyCanvas(SkCanvas* c) : canvas(c) {}
        void onDrawPicture(const SkPicture* picture, const SkMatrix* ,
                               const SkPaint* ) override {
        const SkRect rect = picture->cullRect();
        SkPaint redPaint;
        redPaint.setColor(SK_ColorRED);
        canvas->drawRect(rect, redPaint);
   }

   SkCanvas* canvas;
};
##
SkPictureRecorder recorder;
SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
sk_sp<SkPicture> placeholder = SkPicture::MakePlaceholder({10, 40, 80, 110});
pictureCanvas->drawPicture(placeholder);
sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
MyCanvas myCanvas(canvas);
myCanvas.drawPicture(picture);
##

#SeeAlso MakeFromStream MakeFromData uniqueID

#Method ##

# ------------------------------------------------------------------------------

#Method virtual int approximateOpCount() const = 0
#In Property
#Line # returns approximate operation count ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    picture->playback(canvas);
    std::string opCount = "approximate op count: " + std::to_string(picture->approximateOpCount());
    canvas->drawString(opCount.c_str(), 50, 220, SkPaint());
##

#SeeAlso approximateBytesUsed

#Method ##

# ------------------------------------------------------------------------------

#Method virtual size_t approximateBytesUsed() const = 0
#In Property
#Line # returns approximate size ##
#Populate

#Example
    SkPictureRecorder recorder;
    SkCanvas* pictureCanvas = recorder.beginRecording({0, 0, 256, 256});
    SkPaint paint;
    pictureCanvas->drawRect(SkRect::MakeWH(200, 200), paint);
    paint.setColor(SK_ColorWHITE);
    pictureCanvas->drawRect(SkRect::MakeLTRB(20, 20, 180, 180), paint);
    sk_sp<SkPicture> picture = recorder.finishRecordingAsPicture();
    picture->playback(canvas);
    std::string opCount = "approximate bytes used: " + std::to_string(picture->approximateBytesUsed());
    canvas->drawString(opCount.c_str(), 20, 220, SkPaint());
##

#SeeAlso approximateOpCount

#Method ##

#Class SkPicture ##

#Topic Picture ##