Rose
Animation.h
Go to the documentation of this file.
1 
8 #pragma once
9 
10 #include <array>
11 #include <cstddef>
12 #include <functional>
13 #include <utility>
14 #include <map>
15 #include <vector>
16 #include "constexpertrig.h"
17 #include "GraphicsModel.h"
18 namespace rose {
19 
24  enum class AnimationEnable {
25  Disable, Enable,
26  };
27 
28  namespace ActionCurves {
29  static constexpr float FrameRate = 30.f;
30  constexpr float ac_sin(int t) {
31  return cx_math::sin(cx_math::pi<float> * (float)t / FrameRate);
32  }
33 
34  constexpr float ac_inv_sin(int t) {
35  return 1.f - cx_math::sin(cx_math::pi<float> * (float)t / FrameRate);
36  }
37 
38  class ActionCurve {
39  public:
40  ActionCurve() = default;
41  virtual ~ActionCurve() = default;
42 
43  [[nodiscard]] virtual size_t size() const = 0;
44 
45  virtual float operator[](size_t idx) const = 0;
46  };
47 
48  class PulsePerSecond : public ActionCurve {
49  protected:
50  static constexpr std::array<float, 30> data{
51  ac_sin(0), ac_sin(2), ac_sin(4), ac_sin(6),
52  ac_sin(8), ac_sin(10), ac_sin(12), ac_sin(14),
53  ac_sin(16), ac_sin(18), ac_sin(20), ac_sin(22),
54  ac_sin(24), ac_sin(26), ac_sin(28), 0.f,
55  0.f, 0.f, 0.f, 0.f, 0.f, 0.f,
56  0.f, 0.f, 0.f, 0.f, 0.f, 0.f,
57  0.f, 0.f,
58  };
59 
60  public:
61  ~PulsePerSecond() override = default;
62 
63  [[nodiscard]] size_t size() const override {
64  return data.size();
65  }
66 
67  float operator[](size_t idx) const override {
68  return data[idx];
69  }
70  };
71 
72  class HeartBeat : public ActionCurve {
73  protected:
74  static constexpr std::array<float, 30> data{
75  ac_sin(0), ac_sin(6),ac_sin(12),ac_sin(18),
76  ac_sin(24), 0.f,0.f, 0.f,0.f, 0.f,
77  ac_sin(0), ac_sin(6),ac_sin(12),ac_sin(18),
78  ac_sin(24), 0.f,0.f, 0.f,0.f, 0.f,
79  0.f, 0.f,0.f, 0.f, 0.f, 0.f,
80  0.f, 0.f,0.f, 0.f,
81  };
82 
83  public:
84  ~HeartBeat() override = default;
85 
86  [[nodiscard]] size_t size() const override {
87  return data.size();
88  }
89 
90  float operator[](size_t idx) const override {
91  return data[idx];
92  }
93  };
94 
95  class CursorPulse : public ActionCurve {
96  protected:
97  static constexpr std::array<float, 30> data {
98  ac_inv_sin(0), ac_inv_sin(6),ac_inv_sin(12),ac_inv_sin(18),
99  ac_inv_sin(24), 1.f,1.f, 1.f,1.f, 1.f,
100  1.f,1.f, 1.f,1.f, 1.f, 1.f,
101  1.f,1.f, 1.f,1.f, 1.f, 1.f,
102  1.f,1.f, 1.f,1.f, 1.f, 1.f,
103  1.f,1.f
104  };
105 
106  public:
107  ~CursorPulse() override = default;
108 
109  [[nodiscard]] size_t size() const override {
110  return data.size();
111  }
112 
113  float operator[](size_t idx) const override {
114  return data[idx];
115  }
116  };
117  }
118 
119  template<class Curve, typename ... Args>
120  std::unique_ptr<Curve> curve(Args ... args) {
121  return std::make_unique<Curve>(args ... );
122  }
123 
124  class Animation;
125  class Animator {
126  protected:
127  using AnimationList = std::vector<std::pair<std::shared_ptr<Animation>, Position<int>>>;
128  std::map<std::shared_ptr<Window>,AnimationList> mAnimations;
129 
130  Animator() = default;
131  public:
132  static Animator& getAnimator() {
133  static Animator instance{};
134  return instance;
135  }
136 
137  void set(const std::shared_ptr<Window> &window, std::shared_ptr<Animation> &animation,
138  const Position<int> &position);
139 
140  void remove(const std::shared_ptr<Window>& window, std::shared_ptr<Animation>& animation);
141 
142  void animate(const std::shared_ptr<Window>& window, gm::Context &context, uint32_t frame);
143 
144  explicit operator bool() const noexcept {
145  return !mAnimations.empty();
146  }
147 
148  [[nodiscard]] bool areAnimationsForWindow(const std::shared_ptr<Window>& window) const noexcept {
149  return mAnimations.find(window) != mAnimations.end();
150  }
151  };
152 
157  class Animation {
158  friend class Animator;
159  public:
160  using Callback = std::function<void(gm::Context &context, const Position<int> &, uint32_t frame)>;
161  using Enable = std::function<void(AnimationEnable animationEnable)>;
162 
163  std::unique_ptr<ActionCurves::ActionCurve> mActionCurve{};
164 
165  protected:
166  Callback mAnimationCallback;
167 
168  Enable mAnimationEnableStateCallback;
169 
170  AnimationEnable mAnimationEnableState{AnimationEnable::Disable};
171 
172  public:
173  Animation();
174 
175  virtual ~Animation() = default;
176 
177  static void setAnimation(const std::shared_ptr<Window> &window, std::shared_ptr<Animation> animation,
178  const Position<int> &position) {
179  Animator::getAnimator().set(window, animation, position);
180  }
181 
182  static void removeAnimation(const std::shared_ptr<Window>& window, std::shared_ptr<Animation> animation) {
183  Animator::getAnimator().remove(window, animation);
184  }
185 
186  void setActionCurve(std::unique_ptr<ActionCurves::ActionCurve> &&actionCurve) {
187  mActionCurve = std::move(actionCurve);
188  }
189 
190  void setAnimationEnable(AnimationEnable animationEnable) {
191  mAnimationEnableState = animationEnable;
192  if (mAnimationEnableStateCallback)
193  mAnimationEnableStateCallback(animationEnable);
194  }
195  };
196 }
197 
198 template<class WidgetClass>
199 inline std::shared_ptr<WidgetClass> operator<<(std::shared_ptr<WidgetClass> widget, std::unique_ptr<rose::ActionCurves::ActionCurve>&& curve) {
200  static_assert(std::is_base_of_v<rose::Animation,WidgetClass>, "WidgetClass must be derived from rose::Animation.");
201  widget->setActionCurve(std::move(curve));
202  return widget;
203 }
204 
205 template<class WidgetClass>
206 inline std::shared_ptr<WidgetClass> operator<<(std::shared_ptr<WidgetClass> widget, rose::AnimationEnable animationEnable) {
207  static_assert(std::is_base_of_v<rose::Animation,WidgetClass>, "WidgetClass must be derived from rose::Animation.");
208  widget->setAnimationEnable(animationEnable);
209  return widget;
210 }
AnimationEnable
An enumeration to enable or disable animation.
Definition: Animation.h:24
Definition: Animation.h:95
Definition: Animation.h:157
Context
Definition: GraphicsModel.h:76
Definition: Animation.h:38
Abstraction of the graphics model.
Definition: Animation.h:48
Definition: Animation.h:125
ToDo: There is an issue that the initial scroll interaction is lost if the click/press lands on a Wid...
Definition: CelestialOverlay.cpp:13
Definition: Animation.h:72