blob: 0c20d4a22941d75e70fa74e284c66d3192a56c8e [file] [log] [blame]
reed@google.com889b09e2012-07-27 21:10:42 +00001/*
2 * Copyright 2012 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#ifndef SkSurface_DEFINED
9#define SkSurface_DEFINED
10
11#include "SkRefCnt.h"
12#include "SkImage.h"
13
14class SkCanvas;
15class SkPaint;
reed@google.com5d4ba882012-07-31 15:45:27 +000016class GrContext;
17class GrRenderTarget;
reed@google.com889b09e2012-07-27 21:10:42 +000018
19/**
20 * SkSurface represents the backend/results of drawing to a canvas. For raster
21 * drawing, the surface will be pixels, but (for example) when drawing into
22 * a PDF or Picture canvas, the surface stores the recorded commands.
23 *
24 * To draw into a canvas, first create the appropriate type of Surface, and
25 * then request the canvas from the surface.
26 */
27class SkSurface : public SkRefCnt {
28public:
29 /**
30 * Create a new surface, using the specified pixels/rowbytes as its
31 * backend.
32 *
33 * If the requested surface cannot be created, or the request is not a
34 * supported configuration, NULL will be returned.
35 */
36 static SkSurface* NewRasterDirect(const SkImage::Info&, SkColorSpace*,
37 void* pixels, size_t rowBytes);
38
39 /**
40 * Return a new surface, with the memory for the pixels automatically
41 * allocated.
42 *
43 * If the requested surface cannot be created, or the request is not a
44 * supported configuration, NULL will be returned.
45 */
46 static SkSurface* NewRaster(const SkImage::Info&, SkColorSpace*);
47
48 /**
49 * Return a new surface whose contents will be recorded into a picture.
50 * When this surface is drawn into another canvas, its contents will be
51 * "replayed" into that canvas.
52 */
53 static SkSurface* NewPicture(int width, int height);
54
reed@google.com5d4ba882012-07-31 15:45:27 +000055 /**
56 * Return a new surface using the specified render target.
57 */
58 static SkSurface* NewRenderTargetDirect(GrContext*, GrRenderTarget*);
59
60 /**
61 * Return a new surface whose contents will be drawn to an offscreen
62 * render target, allocated by the surface.
63 */
64 static SkSurface* NewRenderTarget(GrContext*, const SkImage::Info&,
65 SkColorSpace*, int sampleCount = 0);
66
reed@google.com889b09e2012-07-27 21:10:42 +000067 int width() const { return fWidth; }
68 int height() const { return fHeight; }
69
70 /**
71 * Returns a unique non-zero, unique value identifying the content of this
72 * surface. Each time the content is changed changed, either by drawing
73 * into this surface, or explicitly calling notifyContentChanged()) this
74 * method will return a new value.
75 *
76 * If this surface is empty (i.e. has a zero-dimention), this will return
77 * 0.
78 */
79 uint32_t generationID() const;
80
81 /**
82 * Call this if the contents have changed. This will (lazily) force a new
83 * value to be returned from generationID() when it is called next.
84 */
85 void notifyContentChanged();
86
87 /**
reed@google.com9ea5a3b2012-07-30 21:03:46 +000088 * Return a canvas that will draw into this surface. This will always
89 * return the same canvas for a given surface, and is manged/owned by the
90 * surface. It should not be used when its parent surface has gone out of
91 * scope.
reed@google.com889b09e2012-07-27 21:10:42 +000092 */
reed@google.com9ea5a3b2012-07-30 21:03:46 +000093 SkCanvas* getCanvas();
reed@google.com889b09e2012-07-27 21:10:42 +000094
95 /**
96 * Return a new surface that is "compatible" with this one, in that it will
97 * efficiently be able to be drawn into this surface. Typical calling
98 * pattern:
99 *
100 * SkSurface* A = SkSurface::New...();
101 * SkCanvas* canvasA = surfaceA->newCanvas();
102 * ...
103 * SkSurface* surfaceB = surfaceA->newSurface(...);
104 * SkCanvas* canvasB = surfaceB->newCanvas();
105 * ... // draw using canvasB
106 * canvasA->drawSurface(surfaceB); // <--- this will always be optimal!
107 */
108 SkSurface* newSurface(const SkImage::Info&, SkColorSpace*);
109
110 /**
111 * Returns an image of the current state of the surface pixels up to this
112 * point. Subsequent changes to the surface (by drawing into its canvas)
113 * will not be reflected in this image.
114 */
115 SkImage* newImageShapshot();
116
117 /**
118 * Thought the caller could get a snapshot image explicitly, and draw that,
119 * it seems that directly drawing a surface into another canvas might be
120 * a common pattern, and that we could possibly be more efficient, since
121 * we'd know that the "snapshot" need only live until we've handed it off
122 * to the canvas.
123 */
124 void draw(SkCanvas*, SkScalar x, SkScalar y, const SkPaint*);
125
126protected:
127 SkSurface(int width, int height);
128
129private:
130 const int fWidth;
131 const int fHeight;
132 mutable uint32_t fGenerationID;
133};
134
135#endif