New directory tree, with preprocessor/ inside interpretor/.
[Faustine.git] / interpretor / preprocessor / faust-0.9.47mr3 / architecture / gui / GUI.h
diff --git a/interpretor/preprocessor/faust-0.9.47mr3/architecture/gui/GUI.h b/interpretor/preprocessor/faust-0.9.47mr3/architecture/gui/GUI.h
new file mode 100644 (file)
index 0000000..3e9add9
--- /dev/null
@@ -0,0 +1,162 @@
+#ifndef FAUST_GUI_H
+#define FAUST_GUI_H
+
+#include "UI.h"
+#include <list>
+#include <map>
+
+using namespace std;
+
+
+/*******************************************************************************
+ * GUI : Abstract Graphic User Interface
+ * Provides additional macchanismes to synchronize widgets and zones. Widgets
+ * should both reflect the value of a zone and allow to change this value.
+ ******************************************************************************/
+
+struct uiItem;
+typedef void (*uiCallback)(float val, void* data);
+
+class GUI : public UI
+{
+       typedef list<uiItem*> clist;
+       typedef map<float*, clist*> zmap;
+       
+ private:
+       static list<GUI*>       fGuiList;
+       zmap                            fZoneMap;
+       bool                            fStopped;
+       
+ public:
+               
+       GUI() : fStopped(false) {       
+               fGuiList.push_back(this);
+       }
+       
+       virtual ~GUI() {
+               // suppression de this dans fGuiList
+       }
+
+       // -- registerZone(z,c) : zone management
+       
+       void registerZone(float* z, uiItem* c)
+       {
+               if (fZoneMap.find(z) == fZoneMap.end()) fZoneMap[z] = new clist();
+               fZoneMap[z]->push_back(c);
+       }       
+
+       void updateAllZones();
+       
+       void updateZone(float* z);
+       
+       static void updateAllGuis()
+       {
+               list<GUI*>::iterator g;
+               for (g = fGuiList.begin(); g != fGuiList.end(); g++) {
+                       (*g)->updateAllZones();
+               }
+       }
+    void addCallback(float* zone, uiCallback foo, void* data);
+    virtual void show() {};    
+    virtual void run() {};
+       
+       void stop()             { fStopped = true; }
+       bool stopped()  { return fStopped; }
+
+    virtual void declare(float* , const char* , const char* ) {}
+};
+
+
+
+/**
+ * User Interface Item: abstract definition
+ */
+
+class uiItem
+{
+  protected :
+                 
+       GUI*            fGUI;
+       float*          fZone;
+       float           fCache;
+       
+       uiItem (GUI* ui, float* zone) : fGUI(ui), fZone(zone), fCache(-123456.654321) 
+       { 
+               ui->registerZone(zone, this); 
+       }
+       
+       
+  public :
+       virtual ~uiItem() {}
+       
+       void modifyZone(float v)        
+       { 
+               fCache = v;
+               if (*fZone != v) {
+                       *fZone = v;
+                       fGUI->updateZone(fZone);
+               }
+       }
+                       
+       float                   cache()                 { return fCache; }
+       virtual void    reflectZone()   = 0;    
+};
+
+
+/**
+ * Callback Item
+ */
+
+struct uiCallbackItem : public uiItem
+{
+       uiCallback      fCallback;
+       void*           fData;
+       
+       uiCallbackItem(GUI* ui, float* zone, uiCallback foo, void* data) 
+                       : uiItem(ui, zone), fCallback(foo), fData(data) {}
+       
+       virtual void    reflectZone() {         
+               float   v = *fZone;
+               fCache = v; 
+               fCallback(v, fData);    
+       }
+};
+
+// en cours d'installation de call back. a finir!!!!!
+
+/**
+ * Update all user items reflecting zone z
+ */
+
+inline void GUI::updateZone(float* z)
+{
+       float   v = *z;
+       clist*  l = fZoneMap[z];
+       for (clist::iterator c = l->begin(); c != l->end(); c++) {
+               if ((*c)->cache() != v) (*c)->reflectZone();
+       }
+}
+
+
+/**
+ * Update all user items not up to date
+ */
+
+inline void GUI::updateAllZones()
+{
+       for (zmap::iterator m = fZoneMap.begin(); m != fZoneMap.end(); m++) {
+               float*  z = m->first;
+               clist*  l = m->second;
+               float   v = *z;
+               for (clist::iterator c = l->begin(); c != l->end(); c++) {
+                       if ((*c)->cache() != v) (*c)->reflectZone();
+               }
+       }
+}
+
+inline void GUI::addCallback(float* zone, uiCallback foo, void* data) 
+{ 
+       new uiCallbackItem(this, zone, foo, data); 
+};
+
+#endif