1 // Copyright 2017 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef CC_PAINT_SKIA_PAINT_CANVAS_H_
6 #define CC_PAINT_SKIA_PAINT_CANVAS_H_
7 
8 #include <memory>
9 
10 #include "base/compiler_specific.h"
11 #include "build/build_config.h"
12 #include "cc/paint/paint_canvas.h"
13 #include "cc/paint/paint_flags.h"
14 #include "cc/paint/paint_record.h"
15 #include "third_party/skia/include/core/SkCanvas.h"
16 #include "third_party/skia/include/gpu/GrRecordingContext.h"
17 
18 namespace cc {
19 class ImageProvider;
20 class PaintFlags;
21 
22 // A PaintCanvas derived class that passes PaintCanvas APIs through to
23 // an SkCanvas.  This is more efficient than recording to a PaintRecord
24 // and then playing back to an SkCanvas.
25 class CC_PAINT_EXPORT SkiaPaintCanvas final : public PaintCanvas {
26  public:
27   struct CC_PAINT_EXPORT ContextFlushes {
28     ContextFlushes();
29 
30     bool enable;
31     int max_draws_before_flush;
32   };
33 
34   explicit SkiaPaintCanvas(SkCanvas* canvas,
35                            ImageProvider* image_provider = nullptr,
36                            ContextFlushes context_flushes = ContextFlushes());
37   explicit SkiaPaintCanvas(const SkBitmap& bitmap,
38                            ImageProvider* image_provider = nullptr);
39   explicit SkiaPaintCanvas(const SkBitmap& bitmap, const SkSurfaceProps& props);
40   // If |target_color_space| is non-nullptr, then this will wrap |canvas| in a
41   // SkColorSpaceXformCanvas.
42   SkiaPaintCanvas(SkCanvas* canvas,
43                   sk_sp<SkColorSpace> target_color_space,
44                   ImageProvider* image_provider = nullptr,
45                   ContextFlushes context_flushes = ContextFlushes());
46   SkiaPaintCanvas(const SkiaPaintCanvas&) = delete;
47   ~SkiaPaintCanvas() override;
48 
49   SkiaPaintCanvas& operator=(const SkiaPaintCanvas&) = delete;
50 
reset_image_provider()51   void reset_image_provider() { image_provider_ = nullptr; }
52 
53   SkImageInfo imageInfo() const override;
54 
55   void* accessTopLayerPixels(SkImageInfo* info,
56                              size_t* rowBytes,
57                              SkIPoint* origin = nullptr) override;
58 
59   void flush() override;
60 
61   int save() override;
62   int saveLayer(const SkRect* bounds, const PaintFlags* flags) override;
63   int saveLayerAlpha(const SkRect* bounds, uint8_t alpha) override;
64 
65   void restore() override;
66   int getSaveCount() const override;
67   void restoreToCount(int save_count) override;
68   void translate(SkScalar dx, SkScalar dy) override;
69   void scale(SkScalar sx, SkScalar sy) override;
70   void rotate(SkScalar degrees) override;
71   void concat(const SkMatrix& matrix) override;
72   void setMatrix(const SkMatrix& matrix) override;
73 
74   void clipRect(const SkRect& rect, SkClipOp op, bool do_anti_alias) override;
75   void clipRRect(const SkRRect& rrect,
76                  SkClipOp op,
77                  bool do_anti_alias) override;
78   void clipPath(const SkPath& path, SkClipOp op, bool do_anti_alias) override;
79   SkRect getLocalClipBounds() const override;
80   bool getLocalClipBounds(SkRect* bounds) const override;
81   SkIRect getDeviceClipBounds() const override;
82   bool getDeviceClipBounds(SkIRect* bounds) const override;
83   void drawColor(SkColor color, SkBlendMode mode) override;
84   void clear(SkColor color) override;
85 
86   void drawLine(SkScalar x0,
87                 SkScalar y0,
88                 SkScalar x1,
89                 SkScalar y1,
90                 const PaintFlags& flags) override;
91   void drawRect(const SkRect& rect, const PaintFlags& flags) override;
92   void drawIRect(const SkIRect& rect, const PaintFlags& flags) override;
93   void drawOval(const SkRect& oval, const PaintFlags& flags) override;
94   void drawRRect(const SkRRect& rrect, const PaintFlags& flags) override;
95   void drawDRRect(const SkRRect& outer,
96                   const SkRRect& inner,
97                   const PaintFlags& flags) override;
98   void drawRoundRect(const SkRect& rect,
99                      SkScalar rx,
100                      SkScalar ry,
101                      const PaintFlags& flags) override;
102   void drawPath(const SkPath& path, const PaintFlags& flags) override;
103   void drawImage(const PaintImage& image,
104                  SkScalar left,
105                  SkScalar top,
106                  const PaintFlags* flags) override;
107   void drawImageRect(const PaintImage& image,
108                      const SkRect& src,
109                      const SkRect& dst,
110                      const PaintFlags* flags,
111                      SkCanvas::SrcRectConstraint constraint) override;
112   void drawSkottie(scoped_refptr<SkottieWrapper> skottie,
113                    const SkRect& dst,
114                    float t) override;
115   void drawTextBlob(sk_sp<SkTextBlob> blob,
116                     SkScalar x,
117                     SkScalar y,
118                     const PaintFlags& flags) override;
119   void drawTextBlob(sk_sp<SkTextBlob> blob,
120                     SkScalar x,
121                     SkScalar y,
122                     NodeId node_id,
123                     const PaintFlags& flags) override;
124 
125   void drawPicture(sk_sp<const PaintRecord> record) override;
126 
127   bool isClipEmpty() const override;
128   SkMatrix getTotalMatrix() const override;
129 
130   void Annotate(AnnotationType type,
131                 const SkRect& rect,
132                 sk_sp<SkData> data) override;
133 
134   void setNodeId(int) override;
135 
136   // Don't shadow non-virtual helper functions.
137   using PaintCanvas::clipPath;
138   using PaintCanvas::clipRect;
139   using PaintCanvas::clipRRect;
140   using PaintCanvas::drawColor;
141   using PaintCanvas::drawImage;
142   using PaintCanvas::drawPicture;
143 
144   // Same as the above drawPicture() except using the given custom data
145   // raster callback.
146   void drawPicture(
147       sk_sp<const PaintRecord> record,
148       PlaybackParams::CustomDataRasterCallback custom_raster_callback);
149 
150  private:
151   void FlushAfterDrawIfNeeded();
152 
max_texture_size()153   int max_texture_size() const {
154     auto* context = canvas_->recordingContext();
155     return context ? context->maxTextureSize() : 0;
156   }
157 
158   SkCanvas* canvas_;
159   SkBitmap bitmap_;
160   std::unique_ptr<SkCanvas> owned_;
161   ImageProvider* image_provider_ = nullptr;
162 
163   const ContextFlushes context_flushes_;
164   int num_of_ops_ = 0;
165 };
166 
167 }  // namespace cc
168 
169 #endif  // CC_PAINT_SKIA_PAINT_CANVAS_H_
170