diff mde/scheduler/runTime.d @ 23:47478557428d

Implemented drawing a very basic gl box, and only drawing when necessary. Improvements to window resizing, and gl draws a box as a test. Scheduler has "on request" support to redraws only when requested by an event. committer: Diggory Hardy <diggory.hardy@gmail.com>
author Diggory Hardy <diggory.hardy@gmail.com>
date Thu, 27 Mar 2008 10:58:57 +0000
parents 838577503598
children 611f7b9063c6
line wrap: on
line diff
--- a/mde/scheduler/runTime.d	Tue Mar 25 12:24:04 2008 +0000
+++ b/mde/scheduler/runTime.d	Thu Mar 27 10:58:57 2008 +0000
@@ -19,9 +19,20 @@
 
 import tango.time.Time;
 
+debug {
+    import tango.util.log.Log : Log, Logger;
+    private Logger logger;
+}
+static this() {
+    debug logger = Log.getLogger ("mde.scheduler.runTime");
+}
+
+/** Some enums used by per request functions. */
+enum RF_KEYS : uint { DRAW };
+
 // NOTE: Currently has no support for removing functions. To fix, assign ID and store fct pointers
 // in an associative array, returning the ID [on adding fct pointer].
-// FIXME: support delegates or not?
+// NOTE: support delegates or not?
 /// This class can run scheduled functions per frame or every t seconds (sim-time).
 abstract class Scheduler
 {
@@ -49,7 +60,31 @@
     static void perTime (TimeSpan n, scheduleFct fct)
     in { assert (n > TimeSpan (0L)); }
     body {
-        timeFcts ~= TimeFct (fct, n);
+        timeFcts ~= new TimeFct (fct, n);
+    }
+    
+    /** Add a function to be called per requested update.
+    *
+    * A bool parameter is stored locally describing whether or not the function needs recalling,
+    * and is set true upon creation and when requestUpdate is called with the same key. The
+    * function is then called by scheduler's run() whenever this bool variable is true.
+    */
+    static void perRequest (uint key, void function() fct)
+    in {
+        debug if ((key in requestFcts) is null)
+            logger.warn ("perRequest: replacing existing function with same key!");
+    }
+    body {
+        requestFcts[key] = fct;
+        requestFctsUpdate[key] = true;
+    }
+    
+    /** Request an update to request function key. */
+    static void requestUpdate (uint key) {
+        // Note: check the value for this key actually exists
+        bool* p = key in requestFctsUpdate;
+        if (p) *p = true;
+        else debug logger.warn ("requestUpdate called with invalid key");
     }
     
     /** This function should get called by the main loop, once per frame.
@@ -74,10 +109,19 @@
             
             fct.fct (interval);				// call
         }
+        
+        // Call all per-request functions:
+        foreach (key, fct; requestFcts) {
+            if (requestFctsUpdate[key]) {
+                fct();
+                requestFctsUpdate[key] = false;
+            }
+        }
     }
     
-    /* Holds details for functions called per time interval. */
-    private struct TimeFct {
+    /* Holds details for functions called per time interval.
+    * Needs to be a reference type, and using a class is easiest for this. */
+    private static class TimeFct {
         scheduleFct fct;			// function to call
         
         TimeSpan interval;			// interval to call at
@@ -85,15 +129,15 @@
         // be compared to time every frame where fct is not called:
         Time nextCall = Time (0L);
         
-        static TimeFct opCall (scheduleFct f, TimeSpan t) {	// static CTOR
-            TimeFct ret;
-            ret.fct = f;
-            ret.interval = t;
-            return ret;
+        this (scheduleFct f, TimeSpan t) {
+            fct = f;
+            interval = t;
         }
     }
     
     private static Time lastTime = Time (0L);
     private static scheduleFct[] frameFcts;
     private static TimeFct[] timeFcts;
+    private static void function()[uint] requestFcts;
+    private static bool[uint] requestFctsUpdate;    // associated with requestFcts
 }