]> git.localhorst.tv Git - gong.git/blob - src/app/IntervalTimer.hpp
code, assets, and other stuff stolen from blank
[gong.git] / src / app / IntervalTimer.hpp
1 #ifndef GONG_APP_INTERVALTIMER_HPP
2 #define GONG_APP_INTERVALTIMER_HPP
3
4 #include <cmath>
5
6
7 namespace gong {
8 namespace app {
9
10 /// Timer that hits every n Time units. Resolution is that of the
11 /// delta values passed to Update().
12 /// Also tracks the number of iterations as well as Time units
13 /// passed.
14 template<class Time = int>
15 class IntervalTimer {
16
17 public:
18         /// Create a timer that hits every interval Time units.
19         /// Initial state is stopped.
20         explicit IntervalTimer(Time interval_ms = Time(0)) noexcept
21         : intv(interval_ms) { }
22
23         void Start() noexcept {
24                 speed = Time(1);
25         }
26         void Stop() noexcept {
27                 value = Time(0);
28                 speed = Time(0);
29         }
30         void Reset() noexcept {
31                 value = Time(0);
32         }
33
34         bool Running() const noexcept {
35                 return speed != Time(0);
36         }
37         /// true if an interval boundary was passed by the last call to Update()
38         bool Hit() const noexcept {
39                 return Running() && IntervalElapsed() < last_dt;
40         }
41         bool HitOnce() const noexcept {
42                 return Running() && value >= intv;
43         }
44         Time Elapsed() const noexcept {
45                 return value;
46         }
47         Time Interval() const noexcept {
48                 return intv;
49         }
50         Time IntervalElapsed() const noexcept {
51                 return mod(value, intv);
52         }
53         Time IntervalRemain() const noexcept {
54                 return intv - IntervalElapsed();
55         }
56         int Iteration() const noexcept {
57                 return value / intv;
58         }
59         void PopIteration() noexcept {
60                 value -= intv;
61         }
62
63         void Update(Time dt) noexcept {
64                 value += dt * speed;
65                 last_dt = dt;
66         }
67
68         static Time mod(Time val, Time m) noexcept {
69                 return val % m;
70         }
71
72 private:
73         Time intv;
74         Time value = Time(0);
75         Time speed = Time(0);
76         Time last_dt = Time(0);
77
78 };
79
80 using CoarseTimer = IntervalTimer<int>;
81 using FineTimer = IntervalTimer<float>;
82
83 template<>
84 inline float IntervalTimer<float>::mod(float val, float m) noexcept {
85         return std::fmod(val, m);
86 }
87
88 template<>
89 inline int IntervalTimer<float>::Iteration() const noexcept {
90         return std::floor(value / intv);
91 }
92
93 }
94 }
95
96 #endif