comparison mde/scheduler/runTime.d @ 20:838577503598

Reworked much of Init. Moved mde.Init to mde.scheduler.Init and largely cleaned up the code. Implemented mde.scheduler.InitStage to reduce dependancies of modules running Init functions. committer: Diggory Hardy <diggory.hardy@gmail.com>
author Diggory Hardy <diggory.hardy@gmail.com>
date Sat, 22 Mar 2008 16:22:59 +0000
parents
children 47478557428d
comparison
equal deleted inserted replaced
19:db0b48f02b69 20:838577503598
1 /* LICENSE BLOCK
2 Part of mde: a Modular D game-oriented Engine
3 Copyright © 2007-2008 Diggory Hardy
4
5 This program is free software; you can redistribute it and/or modify it under the terms of
6 the GNU General Public License, version 2, as published by the Free Software Foundation.
7
8 This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
9 without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10 See the GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License along
13 with this program; if not, write to the Free Software Foundation, Inc.,
14 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. */
15
16 /** Scheduler
17 */
18 module mde.scheduler.runTime;
19
20 import tango.time.Time;
21
22 // NOTE: Currently has no support for removing functions. To fix, assign ID and store fct pointers
23 // in an associative array, returning the ID [on adding fct pointer].
24 // FIXME: support delegates or not?
25 /// This class can run scheduled functions per frame or every t seconds (sim-time).
26 abstract class Scheduler
27 {
28 /** The type of function pointer to be passed to the scheduler.
29 *
30 * The double $(I time) parameter gives the number of (sim) seconds since the function was last
31 * called, or zero on the first run. */
32 alias void function (double time) scheduleFct;
33
34 /** Add a function to be called per frame. */
35 static void perFrame (scheduleFct fct) {
36 frameFcts ~= fct;
37 }
38
39 /** Add a function to be called per t secs or n 100-nano-sec intevals.
40 *
41 * Since the scheduler cannot guarantee a maximum time between calls, the interval at which
42 * functions are called is always greater than or equal to the inverval specified here. Of
43 * course, the actual inteval is given when the function is run.
44 */
45 static void perTime (double t, scheduleFct fct) {
46 perTime (TimeSpan.interval(t), fct);
47 }
48 /** ditto */
49 static void perTime (TimeSpan n, scheduleFct fct)
50 in { assert (n > TimeSpan (0L)); }
51 body {
52 timeFcts ~= TimeFct (fct, n);
53 }
54
55 /** This function should get called by the main loop, once per frame.
56 *
57 * The parameter time should be the current sim-time, using the tango.core.Types.Time enum; all
58 * time evaluations will use this.
59 */
60 static void run (Time time) {
61 double interval;
62
63 // Call all per-frame functions:
64 if (lastTime == Time (0L)) interval = 0.0; // 0 interval for first loop
65 else interval = (time-lastTime).interval();
66
67 foreach (fct; frameFcts) fct(interval);
68
69 // Call all per-interval functions:
70 foreach (fct; timeFcts) if (time >= fct.nextCall) {
71 if (fct.nextCall == Time (0L)) interval = 0.0; // 0 interval for first call
72 else interval = (time - (fct.nextCall - fct.interval)).interval();
73 fct.nextCall = time + fct.interval; // when to call next
74
75 fct.fct (interval); // call
76 }
77 }
78
79 /* Holds details for functions called per time interval. */
80 private struct TimeFct {
81 scheduleFct fct; // function to call
82
83 TimeSpan interval; // interval to call at
84 // Storing nextCall is more efficient than storing lastCall since only this number has to
85 // be compared to time every frame where fct is not called:
86 Time nextCall = Time (0L);
87
88 static TimeFct opCall (scheduleFct f, TimeSpan t) { // static CTOR
89 TimeFct ret;
90 ret.fct = f;
91 ret.interval = t;
92 return ret;
93 }
94 }
95
96 private static Time lastTime = Time (0L);
97 private static scheduleFct[] frameFcts;
98 private static TimeFct[] timeFcts;
99 }