]> git.mxchange.org Git - simgear.git/blob - simgear/structure/event_mgr.hxx
Fix wrong difference calculation in SGExpression
[simgear.git] / simgear / structure / event_mgr.hxx
1 #ifndef _SG_EVENT_MGR_HXX
2 #define _SG_EVENT_MGR_HXX
3
4 #include <simgear/props/props.hxx>
5 #include <simgear/structure/subsystem_mgr.hxx>
6
7 #include "callback.hxx"
8
9 class SGEventMgr;
10
11 struct SGTimer {
12     std::string name;
13     double interval;
14     SGCallback* callback;
15     SGEventMgr* mgr;
16     bool repeat;
17     bool simtime;
18     void run();
19 };
20
21 class SGTimerQueue {
22 public:
23     SGTimerQueue(int preSize=1);
24     ~SGTimerQueue();
25
26     void update(double deltaSecs);
27
28     double now() { return _now; }
29
30     void     insert(SGTimer* timer, double time);
31     SGTimer* remove(SGTimer* timer);
32     SGTimer* remove();
33
34     SGTimer* nextTimer() { return _numEntries ? _table[0].timer : 0; }
35     double   nextTime()  { return -_table[0].pri; }
36
37     SGTimer* findByName(const std::string& name) const;
38 private:
39     // The "priority" is stored as a negative time.  This allows the
40     // implemenetation to treat the "top" of the heap as the largest
41     // value and avoids developer mindbugs. ;)
42     struct HeapEntry { double pri; SGTimer* timer; };
43
44     int parent(int n) { return ((n+1)/2) - 1; }
45     int lchild(int n) { return ((n+1)*2) - 1; }
46     int rchild(int n) { return ((n+1)*2 + 1) - 1; }
47     double pri(int n) { return _table[n].pri; }
48     void swap(int a, int b) {
49         HeapEntry tmp = _table[a];
50         _table[a] = _table[b];
51         _table[b] = tmp;
52     }
53     void siftDown(int n);
54     void siftUp(int n);
55     void growArray();
56
57     // gcc complains there is no function specification anywhere.
58     // void check();
59
60     double _now;
61     HeapEntry *_table;
62     int _numEntries;
63     int _tableSize;
64 };
65
66 class SGEventMgr : public SGSubsystem
67 {
68 public:
69     SGEventMgr() { _rtProp = 0; }
70     ~SGEventMgr() { _rtProp = 0; }
71
72     virtual void init() {}
73     virtual void update(double delta_time_sec);
74
75     void setRealtimeProperty(SGPropertyNode* node) { _rtProp = node; }
76
77     /**
78      * Add a single function callback event as a repeating task.
79      * ex: addTask("foo", &Function ... )
80      */
81     template<typename FUNC>
82     inline void addTask(const std::string& name, const FUNC& f,
83                         double interval, double delay=0, bool sim=false)
84     { add(name, make_callback(f), interval, delay, true, sim); }
85
86     /**
87      * Add a single function callback event as a one-shot event.
88      * ex: addEvent("foo", &Function ... )
89      */
90     template<typename FUNC>
91     inline void addEvent(const std::string& name, const FUNC& f,
92                          double delay, bool sim=false)
93     { add(name, make_callback(f), 0, delay, false, sim); }
94
95     /**
96      * Add a object/method pair as a repeating task.
97      * ex: addTask("foo", &object, &ClassName::Method, ...)
98      */
99     template<class OBJ, typename METHOD>
100     inline void addTask(const std::string& name,
101                         const OBJ& o, METHOD m,
102                         double interval, double delay=0, bool sim=false)
103     { add(name, make_callback(o,m), interval, delay, true, sim); }
104
105     /**
106      * Add a object/method pair as a repeating task.
107      * ex: addEvent("foo", &object, &ClassName::Method, ...)
108      */
109     template<class OBJ, typename METHOD>
110     inline void addEvent(const std::string& name,
111                          const OBJ& o, METHOD m,
112                          double delay, bool sim=false)
113     { add(name, make_callback(o,m), 0, delay, false, sim); }
114
115
116     void removeTask(const std::string& name);
117 private:
118     friend struct SGTimer;
119
120     void add(const std::string& name, SGCallback* cb,
121              double interval, double delay,
122              bool repeat, bool simtime);
123
124     SGPropertyNode_ptr _freezeProp;
125     SGPropertyNode_ptr _rtProp;
126     SGTimerQueue _rtQueue; 
127     SGTimerQueue _simQueue;
128 };
129
130 #endif // _SG_EVENT_MGR_HXX