blob: a2991f14182db6d3c3c88ff287ef7bd03569f4c2 [file] [log] [blame]
Florin Malitab3418102020-10-15 18:10:29 -04001/*
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#ifndef SkSVGNode_DEFINED
9#define SkSVGNode_DEFINED
10
11#include "include/core/SkRefCnt.h"
12#include "modules/svg/include/SkSVGAttribute.h"
13
14class SkCanvas;
15class SkMatrix;
16class SkPaint;
17class SkPath;
18class SkSVGRenderContext;
19class SkSVGValue;
20
21enum class SkSVGTag {
22 kCircle,
23 kClipPath,
24 kDefs,
25 kEllipse,
26 kG,
27 kLine,
28 kLinearGradient,
29 kPath,
30 kPattern,
31 kPolygon,
32 kPolyline,
33 kRadialGradient,
34 kRect,
35 kStop,
36 kSvg,
37 kText,
38 kUse
39};
40
Florin Malita39fe8c82020-10-20 10:43:03 -040041#define SVG_PRES_ATTR(attr_name, attr_type, attr_inherited) \
42 const attr_type* get##attr_name() const { \
43 return fPresentationAttributes.f##attr_name.getMaybeNull(); \
44 } \
45 void set##attr_name(const attr_type& v) { \
46 if (!attr_inherited || v.type() != attr_type::Type::kInherit) { \
47 fPresentationAttributes.f##attr_name.set(v); \
48 } else { \
49 /* kInherited values are semantically equivalent to \
50 the absence of a local presentation attribute.*/ \
51 fPresentationAttributes.f##attr_name.reset(); \
52 } \
53 } \
54 void set##attr_name(attr_type&& v) { \
55 if (!attr_inherited || v.type() != attr_type::Type::kInherit) { \
56 fPresentationAttributes.f##attr_name.set(std::move(v)); \
57 } else { \
58 /* kInherited values are semantically equivalent to \
59 the absence of a local presentation attribute.*/ \
60 fPresentationAttributes.f##attr_name.reset(); \
61 } \
62 }
63
Florin Malitab3418102020-10-15 18:10:29 -040064class SkSVGNode : public SkRefCnt {
65public:
66 ~SkSVGNode() override;
67
68 SkSVGTag tag() const { return fTag; }
69
70 virtual void appendChild(sk_sp<SkSVGNode>) = 0;
71
72 void render(const SkSVGRenderContext&) const;
73 bool asPaint(const SkSVGRenderContext&, SkPaint*) const;
74 SkPath asPath(const SkSVGRenderContext&) const;
75
76 void setAttribute(SkSVGAttribute, const SkSVGValue&);
77 bool setAttribute(const char* attributeName, const char* attributeValue);
78
79 void setClipPath(const SkSVGClip&);
80 void setClipRule(const SkSVGFillRule&);
81 void setColor(const SkSVGColorType&);
82 void setFill(const SkSVGPaint&);
83 void setFillOpacity(const SkSVGNumberType&);
84 void setFillRule(const SkSVGFillRule&);
85 void setOpacity(const SkSVGNumberType&);
86 void setStroke(const SkSVGPaint&);
87 void setStrokeDashArray(const SkSVGDashArray&);
88 void setStrokeDashOffset(const SkSVGLength&);
89 void setStrokeOpacity(const SkSVGNumberType&);
90 void setStrokeLineCap(const SkSVGLineCap&);
91 void setStrokeLineJoin(const SkSVGLineJoin&);
92 void setStrokeMiterLimit(const SkSVGNumberType&);
93 void setStrokeWidth(const SkSVGLength&);
94 void setVisibility(const SkSVGVisibility&);
95
Florin Malita39fe8c82020-10-20 10:43:03 -040096 SVG_PRES_ATTR(FontFamily, SkSVGFontFamily, true)
97 SVG_PRES_ATTR(FontStyle , SkSVGFontStyle , true)
98 SVG_PRES_ATTR(FontSize , SkSVGFontSize , true)
99 SVG_PRES_ATTR(FontWeight, SkSVGFontWeight, true)
100
Florin Malitab3418102020-10-15 18:10:29 -0400101protected:
102 SkSVGNode(SkSVGTag);
103
104 // Called before onRender(), to apply local attributes to the context. Unlike onRender(),
105 // onPrepareToRender() bubbles up the inheritance chain: overriders should always call
106 // INHERITED::onPrepareToRender(), unless they intend to short-circuit rendering
107 // (return false).
108 // Implementations are expected to return true if rendering is to continue, or false if
109 // the node/subtree rendering is disabled.
110 virtual bool onPrepareToRender(SkSVGRenderContext*) const;
111
112 virtual void onRender(const SkSVGRenderContext&) const = 0;
113
114 virtual bool onAsPaint(const SkSVGRenderContext&, SkPaint*) const { return false; }
115
116 virtual SkPath onAsPath(const SkSVGRenderContext&) const = 0;
117
118 virtual void onSetAttribute(SkSVGAttribute, const SkSVGValue&);
119
120 virtual bool hasChildren() const { return false; }
121
122private:
123 SkSVGTag fTag;
124
125 // FIXME: this should be sparse
126 SkSVGPresentationAttributes fPresentationAttributes;
127
128 using INHERITED = SkRefCnt;
129};
130
Florin Malita385e7442020-10-21 16:55:46 -0400131#undef SVG_PRES_ATTR // presentation attributes are only defined for the base class
132
133#define SVG_ATTR(attr_name, attr_type, attr_default) \
134 private: \
135 attr_type f##attr_name = attr_default; \
136 public: \
137 const attr_type& get##attr_name() const { return f##attr_name; } \
138 void set##attr_name(const attr_type& a) { f##attr_name = a; } \
139 void set##attr_name(attr_type&& a) { f##attr_name = std::move(a); }
140
Florin Malitab3418102020-10-15 18:10:29 -0400141#endif // SkSVGNode_DEFINED