1/*
2 * Copyright 2019 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 SkottieTextAdapter_DEFINED
9#define SkottieTextAdapter_DEFINED
10
11#include "modules/skottie/src/animator/Animator.h"
12#include "modules/skottie/src/text/SkottieShaper.h"
13#include "modules/skottie/src/text/TextAnimator.h"
14#include "modules/skottie/src/text/TextValue.h"
15
16#include <vector>
17
18class SkFontMgr;
19
20namespace sksg {
21class BlurImageFilter;
22class Group;
23template <typename T>
24class Matrix;
25} // namespace sksg
26
27namespace skottie {
28namespace internal {
29
30class TextAdapter final : public AnimatablePropertyContainer {
31public:
32 static sk_sp<TextAdapter> Make(const skjson::ObjectValue&, const AnimationBuilder*,
33 sk_sp<SkFontMgr>, sk_sp<Logger>);
34
35 ~TextAdapter() override;
36
37 const sk_sp<sksg::Group>& node() const { return fRoot; }
38
39 const TextValue& getText() const { return fText.fCurrentValue; }
40 void setText(const TextValue&);
41
42protected:
43 void onSync() override;
44
45private:
46 enum class AnchorPointGrouping : uint8_t {
47 kCharacter,
48 kWord,
49 kLine,
50 kAll,
51 };
52
53 TextAdapter(sk_sp<SkFontMgr>, sk_sp<Logger>, AnchorPointGrouping);
54
55 struct FragmentRec {
56 SkPoint fOrigin; // fragment position
57
58 sk_sp<sksg::Matrix<SkM44>> fMatrixNode;
59 sk_sp<sksg::Color> fFillColorNode,
60 fStrokeColorNode;
61 sk_sp<sksg::BlurImageFilter> fBlur;
62
63 float fAdvance, // used for transform anchor point calculations
64 fAscent; // ^
65 };
66
67 void reshape();
68 void addFragment(const Shaper::Fragment&);
69 void buildDomainMaps(const Shaper::Result&);
70
71 void pushPropsToFragment(const TextAnimator::ResolvedProps&, const FragmentRec&,
72 const SkV2&, const TextAnimator::DomainSpan*) const;
73
74 void adjustLineTracking(const TextAnimator::ModulatorBuffer&,
75 const TextAnimator::DomainSpan&,
76 float line_tracking) const;
77
78 SkV2 fragmentAnchorPoint(const FragmentRec&, const SkV2&,
79 const TextAnimator::DomainSpan*) const;
80 uint32_t shaperFlags() const;
81
82 const sk_sp<sksg::Group> fRoot;
83 const sk_sp<SkFontMgr> fFontMgr;
84 sk_sp<Logger> fLogger;
85 const AnchorPointGrouping fAnchorPointGrouping;
86
87 std::vector<sk_sp<TextAnimator>> fAnimators;
88 std::vector<FragmentRec> fFragments;
89 TextAnimator::DomainMaps fMaps;
90
91 // Helps detect external value changes.
92 struct TextValueTracker {
93 TextValue fCurrentValue;
94
95 bool hasChanged() const {
96 if (fCurrentValue != fPrevValue) {
97 fPrevValue = fCurrentValue;
98 return true;
99 }
100 return false;
101 }
102
103 const TextValue* operator->() const { return &fCurrentValue; }
104
105 private:
106 mutable TextValue fPrevValue;
107 };
108
109 TextValueTracker fText;
110 Vec2Value fGroupingAlignment = {0,0};
111
112 bool fHasBlurAnimator : 1,
113 fRequiresAnchorPoint : 1;
114};
115
116} // namespace internal
117} // namespace skottie
118
119#endif // SkottieTextAdapter_DEFINED
120