• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2020 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 SkRive_DEFINED
9 #define SkRive_DEFINED
10 
11 #include "include/core/SkBlendMode.h"
12 #include "include/core/SkColor.h"
13 #include "include/core/SkM44.h"
14 #include "include/core/SkPaint.h"
15 #include "include/core/SkPathTypes.h"
16 #include "include/core/SkRefCnt.h"
17 #include "include/core/SkString.h"
18 
19 #include <memory>
20 #include <type_traits>
21 #include <vector>
22 
23 class SkCanvas;
24 class SkPaint;
25 class SkStreamAsset;
26 
27 namespace skrive {
28 
29 #define ACTOR_ATTR(attr_name, attr_type, attr_default)               \
30 private:                                                             \
31     attr_type f##attr_name = attr_default;                           \
32 public:                                                              \
33     const attr_type& get##attr_name() const { return f##attr_name; } \
34     void set##attr_name(const attr_type& v) {                        \
35         if (f##attr_name == v) return;                               \
36         f##attr_name = v;                                            \
37         this->invalidate();                                          \
38     }                                                                \
39     void set##attr_name(attr_type&& v) {                             \
40         if (f##attr_name == v) return;                               \
41         f##attr_name = std::move(v);                                 \
42         this->invalidate();                                          \
43     }
44 
45 class Node;
46 
47 class Component : public SkRefCnt {
48 public:
ACTOR_ATTR(Name,SkString,SkString ())49     ACTOR_ATTR(Name, SkString, SkString())
50 
51     template <typename T>
52     std::enable_if_t<std::is_base_of<Component, T>::value, bool>
53     is() const {
54         if constexpr(std::is_same<Component, T>::value) {
55             return true;
56         } else {
57             return is_base_of<T>(fType);
58         }
59     }
60 
61     template <typename T>
62     operator const T*() const {
63         return this->is<T>() ? reinterpret_cast<const T*>(this) : nullptr;
64     }
65 
66     template <typename T>
67     operator T*() {
68         return this->is<T>() ? reinterpret_cast<T*>(this) : nullptr;
69     }
70 
71     void revalidate();
72 
73     // probably not the right place
render(SkCanvas * canvas)74     void render(SkCanvas* canvas) const {
75         this->onRender(canvas);
76     }
77 
78 protected:
79     enum class Type : uint32_t {
80         kNode,
81         kShape,
82         kColorPaint,
83         kEllipse,
84         kRectangle,
85     };
86 
Component(Type t)87     explicit Component(Type t) : fType(t) {}
88 
89     void invalidate();
90 
hasInval()91     bool hasInval() const { return fDirty; }
92 
93     virtual void onRevalidate() = 0;
94     virtual void onRender(SkCanvas*) const;
95 
96 private:
97     friend class Node; // parent access
98 
99     template <typename T>
100     static constexpr bool is_base_of(Type t);
101 
102     const Type  fType;
103 
104     Node* fParent = nullptr;
105     bool  fDirty  = true;
106 };
107 
108 class TransformableComponent : public Component {
109 public:
110     ACTOR_ATTR(Translation        , SkV2 , SkV2({0, 0}))
111     ACTOR_ATTR(Scale              , SkV2 , SkV2({1, 1}))
112     ACTOR_ATTR(Rotation           , float, 0           )
113     ACTOR_ATTR(Opacity            , float, 1           )
114 
115 protected:
TransformableComponent(Type t)116     explicit TransformableComponent(Type t) : INHERITED(t) {}
117 
118     class ScopedTransformContext final {
119     public:
120         ScopedTransformContext(const TransformableComponent*, SkCanvas*);
121         ~ScopedTransformContext();
122 
123     private:
124         SkCanvas* fCanvas;
125         const int fRestoreCount;
126     };
127 
128 private:
129     using INHERITED = Component;
130 };
131 
132 class Node : public TransformableComponent {
133 public:
Node()134     Node() : INHERITED(Type::kNode) {}
135 
136     ACTOR_ATTR(CollapsedVisibility, bool , false       )
137 
138     void addChild(sk_sp<Component>);
139 
children()140     const std::vector<sk_sp<Component>>& children() const { return fChildren; }
141 
142 protected:
Node(Type t)143     explicit Node(Type t) : INHERITED(t) {}
144 
145     void onRevalidate() override;
146 
147     void onRender(SkCanvas*) const override;
148 
149 private:
150     std::vector<sk_sp<Component>> fChildren;
151 
152     using INHERITED = TransformableComponent;
153 };
154 
155 class Paint : public Component {
156 public:
157     ACTOR_ATTR(Opacity    , float         , 1                         )
158     ACTOR_ATTR(FillRule   , SkPathFillType, SkPathFillType::kWinding  )
159     ACTOR_ATTR(StrokeWidth, float         , 1                         )
160     ACTOR_ATTR(StrokeCap  , SkPaint::Cap  , SkPaint::Cap::kButt_Cap   )
161     ACTOR_ATTR(StrokeJoin , SkPaint::Join , SkPaint::Join::kMiter_Join)
162 
163     enum class StrokeTrim : uint8_t { kOff, kSequential, kSynced };
ACTOR_ATTR(StrokeTrim,StrokeTrim,StrokeTrim::kOff)164     ACTOR_ATTR(StrokeTrim      , StrokeTrim, StrokeTrim::kOff)
165     ACTOR_ATTR(StrokeTrimStart , float     , 0)
166     ACTOR_ATTR(StrokeTrimEnd   , float     , 0)
167     ACTOR_ATTR(StrokeTrimOffset, float     , 0)
168 
169     void apply(SkPaint* paint) const {
170         this->onApply(paint);
171     }
172 
style()173     SkPaint::Style style() const { return fStyle; }
174 
175 protected:
Paint(Type t,SkPaint::Style style)176     Paint(Type t, SkPaint::Style style) : INHERITED(t), fStyle(style) {}
177 
178     virtual void onApply(SkPaint*) const;
179 
180 private:
181     const SkPaint::Style fStyle;
182 
183     using INHERITED = Component;
184 };
185 
186 class ColorPaint final : public Paint {
187 public:
ColorPaint(SkPaint::Style style)188     explicit ColorPaint(SkPaint::Style style) : INHERITED(Type::kColorPaint, style) {}
189 
190     ACTOR_ATTR(Color, SkColor4f, SkColors::kBlack)
191 
192 private:
193     void onRevalidate() override;
194 
195     void onApply(SkPaint*) const override;
196 
197     using INHERITED = Paint;
198 };
199 
200 class Geometry : public Node {
201 public:
draw(SkCanvas * canvas,const SkPaint & paint,SkPathFillType ftype)202     void draw(SkCanvas* canvas, const SkPaint& paint, SkPathFillType ftype) const {
203         return this->onDraw(canvas, paint, ftype);
204     }
205 
206 protected:
Geometry(Type t)207     explicit Geometry(Type t) : INHERITED(t) {}
208 
209     virtual void onDraw(SkCanvas*, const SkPaint&, SkPathFillType) const = 0;
210 
211 private:
212     using INHERITED = Node;
213 };
214 
215 class Ellipse final : public Geometry {
216 public:
Ellipse()217     Ellipse() : INHERITED(Type::kEllipse) {}
218 
219     ACTOR_ATTR(Width , float, 0)
220     ACTOR_ATTR(Height, float, 0)
221 
222 private:
223     void onRevalidate() override;
224     void onDraw(SkCanvas*, const SkPaint&, SkPathFillType) const override;
225 
226     using INHERITED = Geometry;
227 };
228 
229 class Rectangle final : public Geometry {
230 public:
Rectangle()231     Rectangle() : INHERITED(Type::kRectangle) {}
232 
233     ACTOR_ATTR(Width , float, 0)
234     ACTOR_ATTR(Height, float, 0)
235     ACTOR_ATTR(Radius, float, 0)
236 
237 private:
238     void onRevalidate() override;
239     void onDraw(SkCanvas*, const SkPaint&, SkPathFillType) const override;
240 
241     using INHERITED = Geometry;
242 };
243 
244 class Drawable : public Node {
245 public:
246     ACTOR_ATTR(DrawOrder, size_t     , 0                    )
ACTOR_ATTR(BlendMode,SkBlendMode,SkBlendMode::kSrcOver)247     ACTOR_ATTR(BlendMode, SkBlendMode, SkBlendMode::kSrcOver)
248     ACTOR_ATTR(IsHidden , bool       , false                )
249 
250 protected:
251     explicit Drawable(Type t) : INHERITED(t) {}
252 
253 private:
254     using INHERITED = Node;
255 };
256 
257 class Shape final : public Drawable {
258 public:
Shape()259     Shape() : INHERITED(Type::kShape) {}
260 
261     ACTOR_ATTR(TransformAffectsStroke, bool, true)
262 
263 private:
264     void onRevalidate() override;
265     void onRender(SkCanvas*) const override;
266 
267     // cached on revalidation
268     // tracked separately due to paint order (all fills before strokes)
269     std::vector<const Paint*>    fFills,
270                                  fStrokes;
271 
272     std::vector<const Geometry*> fGeometries;
273 
274     using INHERITED = Drawable;
275 };
276 
277 template <typename T>
is_base_of(Type t)278 constexpr bool Component::is_base_of(Type t) {
279     if (t == Type::kNode      ) return std::is_base_of<T, Node      >::value;
280     if (t == Type::kShape     ) return std::is_base_of<T, Shape     >::value;
281     if (t == Type::kColorPaint) return std::is_base_of<T, ColorPaint>::value;
282     if (t == Type::kEllipse   ) return std::is_base_of<T, Ellipse   >::value;
283     if (t == Type::kRectangle ) return std::is_base_of<T, Rectangle >::value;
284 
285     return false;
286 }
287 
288 class Artboard final : public SkRefCnt {
289 public:
290     ACTOR_ATTR(Root        , sk_sp<Node>, nullptr         )
291     ACTOR_ATTR(Name        , SkString   , SkString()      )
292     ACTOR_ATTR(Color       , SkColor4f  , SkColors::kBlack)
293     ACTOR_ATTR(Size        , SkV2       , SkV2({0,0})     )
294     ACTOR_ATTR(Origin      , SkV2       , SkV2({0,0})     )
295     ACTOR_ATTR(Translation , SkV2       , SkV2({0,0})     )
296     ACTOR_ATTR(ClipContents, bool       , false           )
297 
298     void render(SkCanvas*) const;
299 
300 private:
invalidate()301     void invalidate() {}
302 };
303 
304 class SK_API SkRive final : public SkNVRefCnt<SkRive> {
305 public:
306     class Builder final {
307     public:
308         sk_sp<SkRive> make(std::unique_ptr<SkStreamAsset>);
309     };
310 
artboards()311     const std::vector<sk_sp<Artboard>>& artboards() const { return fArtboards; }
artboards()312           std::vector<sk_sp<Artboard>>& artboards()       { return fArtboards; }
313 
314 private:
315     std::vector<sk_sp<Artboard>> fArtboards;
316 };
317 
318 }  // namespace skrive
319 
320 #endif // SkRive_DEFINED
321