Browse Source

Add tlCtl and libcmpp to this repo.

master
kevin 3 years ago
parent
commit
f2ea644147

+ 0
- 2
.gitignore View File

@@ -1,7 +1,5 @@
1 1
 # directories to ignore
2 2
 libcm
3
-libcmpp
4
-tlCtl
5 3
 
6 4
 .deps
7 5
 autom4te.cache

+ 2
- 2
Makefile.am View File

@@ -55,8 +55,8 @@ endif
55 55
 endif
56 56
 
57 57
 if OS_OSX
58
- AM_CPPFLAGS +=  -I/opt/local/include	
59
- AM_LDFLAGS  +=  -L/opt/local/lib
58
+ AM_CPPFLAGS +=  -I/opt/local/include	# Search macports directory for fftw headers
59
+ AM_LDFLAGS  +=  -L/opt/local/lib       # and libraries.
60 60
  AM_LDFLAGS  +=  -framework Cocoa -framework CoreAudio -framework CoreMIDI -framework Carbon -framework Accelerate
61 61
 endif
62 62
 

+ 1
- 0
src/libcmpp/.gitignore View File

@@ -0,0 +1 @@
1
+Makefile.in

+ 18
- 0
src/libcmpp/Makefile.am View File

@@ -0,0 +1,18 @@
1
+
2
+
3
+cmppSRC  = src/libcmpp/fltk/Fl_CbLinker.cpp src/libcmpp/fltk/Fl_Splitter.cpp
4
+cmppHDR  = src/libcmpp/fltk/Fl_CbLinker.h   src/libcmpp/fltk/Fl_Splitter.h
5
+
6
+cmppSRC += src/libcmpp/fltk/cmGrFltk.cpp
7
+cmppHDR += src/libcmpp/fltk/cmGrFltk.h
8
+
9
+cmppHDR += src/libcmpp/fltk/Fl_File_Btn.h    src/libcmpp/fltk/Fl_Vert_Progress.h
10
+cmppSRC += src/libcmpp/fltk/Fl_File_Btn.cpp  src/libcmpp/fltk/Fl_Vert_Progress.cpp
11
+
12
+cmppHDR += src/libcmpp/fltk/Fl_DevCfgGroup.h 
13
+cmppSRC += src/libcmpp/fltk/Fl_DevCfgGroup.cpp
14
+
15
+cmppHDR += src/libcmpp/fltk/cmUiDrvrFltk.h
16
+cmppSRC += src/libcmpp/fltk/cmUiDrvrFltk.cpp
17
+
18
+

+ 82
- 0
src/libcmpp/fltk/Fl_CbLinker.cpp View File

@@ -0,0 +1,82 @@
1
+#include <FL/Fl.H>
2
+#include <FL/Fl_Widget.H>
3
+#include <FL/Fl_Button.H>
4
+#include <FL/Fl_Scrollbar.H>
5
+#include <FL/Fl_Menu_Button.H>
6
+#include <FL/Fl_Menu_Item.H>
7
+
8
+#include <vector>
9
+#include <assert.h>
10
+#include "Fl_CbLinker.h"
11
+
12
+
13
+Fl_CbLinker::Fl_CbLinker()
14
+{}
15
+
16
+Fl_CbLinker::~Fl_CbLinker()
17
+{
18
+  unsigned i;
19
+  for(i=0; i<_ctlV.size(); ++i)
20
+    delete _ctlV[i];
21
+}
22
+
23
+void Fl_CbLinker::registerCtl( Fl_Button* c, unsigned id )
24
+{ 
25
+  ctl_t* r;
26
+  _ctlV.push_back( r = new ctl_t(this,c,id) ); 
27
+  c->callback(_s_callback,r);
28
+}
29
+
30
+void Fl_CbLinker::registerCtl( Fl_Scrollbar* c, unsigned id ) 
31
+{ 
32
+  ctl_t* r;
33
+  _ctlV.push_back( r = new ctl_t(this,c,id) ); 
34
+  c->callback(_s_callback,r);
35
+}
36
+
37
+void Fl_CbLinker::registerCtl( Fl_Menu_Button* c, unsigned id ) 
38
+{ 
39
+  ctl_t* r;
40
+  _ctlV.push_back( r = new ctl_t(this,c,id) ); 
41
+  c->callback(_s_callback,r);
42
+}
43
+
44
+void Fl_CbLinker::registerCtl( Fl_Menu_Item* c, unsigned id ) 
45
+{ 
46
+  ctl_t* r;
47
+  _ctlV.push_back( r = new ctl_t(this,c,id) ); 
48
+  c->callback(_s_callback,r);
49
+}
50
+
51
+void Fl_CbLinker::onButton( Fl_Button* c, unsigned id )
52
+{}
53
+
54
+void Fl_CbLinker::onScrollbar( Fl_Scrollbar* c, unsigned id )
55
+{}
56
+
57
+void Fl_CbLinker::onMenuBtn( Fl_Menu_Button* c, unsigned id )
58
+{}
59
+
60
+void Fl_CbLinker::onMenuItem( Fl_Menu_Item* c, unsigned id )
61
+{}
62
+
63
+
64
+void Fl_CbLinker::_s_callback( Fl_Widget* w, void* arg )
65
+{
66
+  ctl_t* r =  static_cast<ctl_t*>(arg);
67
+
68
+  unsigned i;
69
+  for(i=0; i<r->thisPtr->_ctlV.size(); ++i)
70
+    if( r->thisPtr->_ctlV[i] == arg )
71
+    {
72
+      switch( r->typeId )
73
+      {
74
+        case kButtonTId:    r->thisPtr->onButton(    r->u.btn,   r->ctlId); break;
75
+        case kScrollbarTId: r->thisPtr->onScrollbar( r->u.sb,    r->ctlId); break;
76
+        case kMenuBtnTId:   r->thisPtr->onMenuBtn(   r->u.mbtn,  r->ctlId); break;
77
+        case kMenuItemTId:  r->thisPtr->onMenuItem(  r->u.mitem, r->ctlId); break;
78
+        default:
79
+          { assert(0); }
80
+      }
81
+    }
82
+}

+ 72
- 0
src/libcmpp/fltk/Fl_CbLinker.h View File

@@ -0,0 +1,72 @@
1
+#ifndef Fl_CbLinker_h
2
+#define Fl_CbLinker_h
3
+
4
+class Fl_Widget;
5
+class Fl_Button;
6
+class Fl_Scrollbar;
7
+class Fl_Menu_Button;
8
+struct Fl_Menu_Item;
9
+
10
+/* 
11
+This class solves the problem of linking static control callback functions
12
+to an object instance. 
13
+
14
+registerCtl() creates a record which links a control to an instance
15
+of a Fl_CbLinker. The control is then given a static callback function:
16
+_s_callback().  When _s_callback() is called from the control event
17
+handler it links locates the controls link record an calls the
18
+appropriate handler (e.g. onButton(), onScrollBar(), etc.)
19
+*/
20
+
21
+class Fl_CbLinker
22
+{
23
+ public:
24
+  Fl_CbLinker();
25
+  virtual ~Fl_CbLinker();
26
+
27
+  void registerCtl( Fl_Button*      c, unsigned id );
28
+  void registerCtl( Fl_Scrollbar*   c, unsigned id ); 
29
+  void registerCtl( Fl_Menu_Button* c, unsigned id );
30
+  void registerCtl( Fl_Menu_Item*   c, unsigned id );
31
+
32
+  virtual void onButton(    Fl_Button*      c, unsigned id );
33
+  virtual void onScrollbar( Fl_Scrollbar*   c, unsigned id );
34
+  virtual void onMenuBtn(   Fl_Menu_Button* c, unsigned id );
35
+  virtual void onMenuItem(  Fl_Menu_Item*   c, unsigned id );
36
+
37
+ private:
38
+  enum
39
+  {
40
+    kButtonTId,
41
+    kScrollbarTId,
42
+    kMenuBtnTId,
43
+    kMenuItemTId
44
+  };
45
+
46
+  typedef struct ctl_str
47
+  {
48
+    Fl_CbLinker* thisPtr;
49
+    unsigned     typeId;
50
+    unsigned     ctlId;
51
+    union
52
+    {
53
+      Fl_Button*      btn;
54
+      Fl_Scrollbar*   sb;
55
+      Fl_Menu_Button* mbtn;
56
+      Fl_Menu_Item*   mitem;
57
+      Fl_Widget*      w;
58
+    } u;
59
+
60
+  ctl_str( Fl_CbLinker* t, Fl_Button*      c, unsigned id)  : thisPtr(t), typeId(kButtonTId),   ctlId(id) { u.btn=c; }
61
+  ctl_str( Fl_CbLinker* t, Fl_Scrollbar*   c, unsigned id ) : thisPtr(t), typeId(kScrollbarTId),ctlId(id) { u.sb=c; }
62
+  ctl_str( Fl_CbLinker* t, Fl_Menu_Button* c, unsigned id ) : thisPtr(t), typeId(kMenuBtnTId),  ctlId(id) { u.mbtn=c; }
63
+  ctl_str( Fl_CbLinker* t, Fl_Menu_Item*   c, unsigned id ) : thisPtr(t), typeId(kMenuItemTId), ctlId(id) { u.mitem=c; }
64
+
65
+  } ctl_t;
66
+
67
+  std::vector< ctl_t* > _ctlV;
68
+
69
+  static void _s_callback( Fl_Widget* w, void* arg );
70
+};
71
+
72
+#endif

+ 1135
- 0
src/libcmpp/fltk/Fl_DevCfgGroup.cpp
File diff suppressed because it is too large
View File


+ 168
- 0
src/libcmpp/fltk/Fl_DevCfgGroup.h View File

@@ -0,0 +1,168 @@
1
+#ifndef Fl_DevCfgGroup_h
2
+#define Fl_DevCfgGroup_h
3
+
4
+#include <vector>
5
+
6
+class Fl_DevCfgGroup : public Fl_Group
7
+{
8
+public:
9
+  Fl_DevCfgGroup(cmDevCfgH_t dcH, int x, int y, int w, int h, const char* label );
10
+  virtual ~Fl_DevCfgGroup();
11
+
12
+  void onEnableAudio(bool enableFl );
13
+
14
+private:
15
+  enum
16
+  {
17
+    kInvalidCId,
18
+    kLocLabelCId,
19
+    kLocMenuCId,
20
+    kLocStringCId,
21
+    kLocStoreBtnCId,
22
+    kLocDeleteBtnCId,
23
+
24
+    kMidiLabelCId,
25
+    kMidiCfgMenuCId,
26
+    kMidiDeleteBtnCId,
27
+    kMidiCfgStringCId,
28
+    kMidiApplyBtnCId,
29
+    kMidiCfgDescCId,
30
+    kMidiDevMenuCId,
31
+    kMidiDevLabelCId,
32
+    kMidiPortMenuCId,
33
+    kMidiPortLabelCId,
34
+    kMidiInputCheckCId,
35
+
36
+    kAudioLabelCId,
37
+    kAudioCfgMenuCId,
38
+    kAudioDeleteBtnCId,
39
+    kAudioCfgDescCId,
40
+    kAudioCfgStringCId,
41
+    kAudioApplyBtnCId,
42
+    kAudioInDevMenuCId,
43
+    kAudioInDevLabelCId,
44
+    kAudioOutDevMenuCId,
45
+    kAudioOutDevLabelCId,
46
+    kAudioMsgQueSizeValCId,
47
+    kAudioDevFpCValCId,
48
+    kAudioDspFpCValCId,
49
+    kAudioBufCntValCId,
50
+    kAudioSrateMenuCId,
51
+    kAudioSyncInCheckCId,
52
+    kAudioNetNodeStringCId,
53
+    kAudioBcastAddrStringCId,
54
+    kAudioIpAddrStringCId,
55
+    kAudioIpPortValCId,
56
+    kAudioActiveCheckCId,
57
+
58
+    /*
59
+    kNetLabelCId,
60
+    kNetCfgMenuCId,
61
+    kNetDeleteBtnCId,
62
+    kNetCfgDescCId,
63
+    kNetCfgStringCId,
64
+    kNetApplyBtnCId,
65
+    kNetSockAddrStringCId,
66
+    kNetPortNumbValCId,
67
+    kNetLocalCheckCId,
68
+    kNetActiveCheckCId
69
+    */
70
+
71
+  };
72
+
73
+  typedef struct
74
+  {
75
+    unsigned        id;
76
+    Fl_DevCfgGroup* p;
77
+    union
78
+    {
79
+      Fl_Button*       btn;
80
+      Fl_Check_Button* chk;
81
+      Fl_Box*          box;
82
+      Fl_Menu_Button*  mbt;
83
+      Fl_Input*        inp;
84
+      Fl_Value_Input*  val;
85
+    } u;
86
+    
87
+  } ctl_t;
88
+
89
+  cmDevCfgH_t           _dcH;
90
+  std::vector< ctl_t* > _ctlV;
91
+  
92
+  bool     _loadLocBtn();
93
+  void     _recallLoc();
94
+  void     _storeLoc();
95
+  void     _deleteLoc();
96
+
97
+  void     _loadMidiDevBtn();
98
+  void     _loadMidiPortBtn();
99
+  void     _loadAudioDevBtn( unsigned id, unsigned devIdx );
100
+  void     _loadAudioSrateBtn();
101
+  void     _loadCfgMenu(cmTypeDcmId_t typeId, unsigned menuCtlId, unsigned deleteCtlId );
102
+  void     _syncLoc();
103
+  void     _createMidiCfg();
104
+  void     _createAudioCfg();
105
+  //void     _createNetCfg();
106
+  void     _deleteCfg( cmTypeDcmId_t typeId, unsigned menuCtlId, unsigned inpCtlCId, unsigned descCtlId, unsigned storeCtlId, unsigned deleteCtlId );
107
+  void     _recallCfg( cmTypeDcmId_t typeId, unsigned menuCtlId, unsigned strCtlId, unsigned descCtlId, unsigned storeCtlId );
108
+
109
+  // Attempt to set the menu to index 'val' otherwise attempt to set it to 'dfltVal'
110
+  // Finish by updating the label.
111
+  void     _restoreMenuValue( unsigned menuCtlId, int val, int dfltVal=0 );
112
+
113
+  // Get the current string value of the menu btn.
114
+  const char* _menuBtnValueStr( unsigned menuCtlId );
115
+
116
+  // Copy the menu btn's current string value to the label (and the input control)
117
+  void        _setMenuBtnLabel( unsigned menuCtlId, unsigned inpCtlId = cmInvalidId );
118
+
119
+  // Set the menu buttons value to 'string' and update the menu btn's label
120
+  void        _setMenuBtnWithString( unsigned menuCtlId, const char* string );
121
+  void        _setCheckCtl( unsigned ctlId, int val );
122
+  void        _setValueCtl( unsigned ctlId, double val );
123
+  void        _setInputCtl( unsigned ctlId, const cmChar_t* val );
124
+
125
+  const cmChar_t* _getMenuCtl(  unsigned ctlId );
126
+  const cmChar_t* _getInputCtl( unsigned ctlId );
127
+  double          _getValueCtl( unsigned ctlId );
128
+  bool            _getCheckCtl( unsigned ctlId );
129
+
130
+  double      _getSrate();
131
+  void        _setSrate( double srate );
132
+
133
+  void        _enableStoreBtn( unsigned ctlId );
134
+
135
+  ctl_t*   _idToCtl(unsigned id);
136
+  
137
+  
138
+  static void _s_ctl_cb( Fl_Widget* w, void* arg );
139
+  
140
+};
141
+
142
+// Init:
143
+//   1) Load all menu X btns and set to first entry.
144
+//   2) set cfg string X to string value of cfg menu
145
+//   3) update desc and X fields.
146
+//
147
+// Cfg:
148
+// Store:
149
+//   1) call cmDevCfgNameX( cfg_label ) successfully
150
+//   2) reload cfg menu
151
+//   3) set cfg menu label to new cfg_label
152
+// 
153
+// Recall:
154
+//   1) set cfg menu X label
155
+//   2) set cfg string X to string value of cfg menu
156
+//   3) update desc and X fields
157
+//
158
+// Delete:
159
+//   1) call cmDevDeleteX( cfg_label ) sucessfuly.
160
+//   2) reload cfg menu and set to first entry
161
+//   3) set cfg string X to string value of cfg menu
162
+//   4) update desc and X fields
163
+//
164
+// 
165
+
166
+
167
+
168
+#endif

+ 105
- 0
src/libcmpp/fltk/Fl_File_Btn.cpp View File

@@ -0,0 +1,105 @@
1
+#include <Fl/Fl.H>
2
+#include <Fl/Fl_Button.H>
3
+#include <Fl/Fl_File_Chooser.H>
4
+#include <Fl/Fl_Output.H>
5
+#include <Fl/Fl_Group.H>
6
+#include "Fl_File_Btn.h"
7
+
8
+Fl_File_Btn::Fl_File_Btn( int xx, int yy, int ww, int hh, const char* l )
9
+  : Fl_Group(xx,yy,ww,hh,l),
10
+    _patStr(NULL),_typeId(kFile_Type_Id),_btn(NULL),_out(NULL)
11
+{
12
+  _init();
13
+  end();
14
+}
15
+
16
+Fl_File_Btn::Fl_File_Btn( unsigned typeId, const char* patStr, int xx, int yy, int ww, int hh, const char* l )
17
+  : Fl_Group(xx,yy,ww,hh,l),
18
+    _patStr(NULL),_typeId(typeId),_btn(NULL),_out(NULL)
19
+{
20
+  _init();
21
+  type(typeId);
22
+  pattern_string(patStr);
23
+  end();
24
+}
25
+
26
+Fl_File_Btn::~Fl_File_Btn()
27
+{ delete[] _patStr; }
28
+
29
+unsigned    Fl_File_Btn::type()
30
+{ return _typeId; }
31
+
32
+void        Fl_File_Btn::type( unsigned typeId )
33
+{
34
+  switch(typeId)
35
+  {
36
+    case kFile_Type_Id:
37
+      _btn->label("File");
38
+      _typeId = typeId;
39
+      break;
40
+
41
+    case kDir_Type_Id:
42
+      _btn->label("Dir");
43
+      _typeId = typeId;
44
+      break;
45
+  }
46
+
47
+  
48
+}
49
+
50
+const char* Fl_File_Btn::pattern_string()
51
+{ return _patStr;  }
52
+
53
+void        Fl_File_Btn::pattern_string( const char* pat)
54
+{
55
+  delete[] _patStr;
56
+  if( pat != NULL )
57
+  {
58
+    _patStr = new char[ strlen(pat) + 1];
59
+    strcpy(_patStr,pat);
60
+  }
61
+}
62
+
63
+void        Fl_File_Btn::btn_width( int ww )
64
+{ 
65
+  _btn->resize(_btn->x(),_btn->y(),ww,_btn->h());
66
+  _out->resize(_btn->x() + _btn->w() + 2, _out->y(), w() - _btn->w() - 2, _out->h());
67
+}
68
+
69
+int         Fl_File_Btn::btn_width()
70
+{ return _btn->w(); }
71
+
72
+void        Fl_File_Btn::filename( const char* fn )
73
+{ _out->value(fn); _out->redraw(); }
74
+
75
+const char* Fl_File_Btn::filename() const
76
+{ return _out->value(); }
77
+
78
+
79
+void Fl_File_Btn::_s_btn_cb(Fl_Widget* w, void* data)
80
+{ ((Fl_File_Btn*)data)->_btn_cb(); }
81
+
82
+void Fl_File_Btn::_btn_cb()
83
+{
84
+  char* fn;
85
+  if( _typeId == kFile_Type_Id )
86
+    fn = fl_file_chooser("Select a file",_patStr,_out->value(),0);
87
+  else
88
+    fn = fl_dir_chooser("Select a directory",_out->value(),0);
89
+
90
+  if( fn != NULL )
91
+  {
92
+    _out->value(fn);
93
+    do_callback(this,user_data());
94
+  }
95
+
96
+}
97
+
98
+void Fl_File_Btn::_init()
99
+{
100
+  _btn = new Fl_Button(x(),y(),40,h(),_typeId==kFile_Type_Id ? "File" : "Dir");
101
+  _btn->callback(_s_btn_cb,this);
102
+
103
+  _out = new Fl_Output(x() + _btn->w() + 2, y(), w() - _btn->w(), h());
104
+
105
+}

+ 47
- 0
src/libcmpp/fltk/Fl_File_Btn.h View File

@@ -0,0 +1,47 @@
1
+#ifndef Fl_File_Btn_h
2
+#define Fl_File_Btn_h
3
+
4
+class Fl_Button;
5
+class Fl_Output;
6
+
7
+class Fl_File_Btn : public Fl_Group
8
+{
9
+public:
10
+  enum
11
+  {
12
+    kFile_Type_Id,
13
+    kDir_Type_Id
14
+  };
15
+
16
+  Fl_File_Btn( int x, int y, int w, int h, const char* l = 0 );
17
+
18
+  Fl_File_Btn( unsigned typeId, const char* patStr, int x, int y, int w, int h, const char* l = 0 );
19
+  virtual ~Fl_File_Btn();
20
+
21
+  unsigned    type();
22
+  void        type( unsigned typeId );
23
+
24
+  const char* pattern_string();
25
+  void        pattern_string( const char* pat);
26
+
27
+  void        btn_width( int w );
28
+  int         btn_width();
29
+
30
+  void        filename( const char* fn );
31
+  const char* filename() const;
32
+
33
+private:
34
+  char*       _patStr;
35
+  unsigned    _typeId;
36
+  Fl_Button*  _btn;
37
+  Fl_Output*  _out;
38
+
39
+  static void _s_btn_cb(Fl_Widget* w, void* data);
40
+  void _btn_cb();
41
+
42
+  void _init();
43
+
44
+};
45
+
46
+
47
+#endif

+ 273
- 0
src/libcmpp/fltk/Fl_Splitter.cpp View File

@@ -0,0 +1,273 @@
1
+// Code based on: http://www.mail-archive.com/fltk@easysw.com/msg04573.html
2
+// Lucas Sanner/Ian MacArthur
3
+
4
+#include "Fl_Splitter.h"
5
+
6
+void Fl_HSplitter::draw()
7
+{
8
+  Fl_Group::draw();
9
+  Fl_Color c = fl_color();
10
+  fl_color(FL_BLACK);
11
+  fl_line_style( FL_DOT, 1);
12
+
13
+  if(splitFl && Fl::event_button1() != 0)
14
+  {
15
+    fl_push_clip(x(), y(), w(), h());
16
+
17
+    yPos = Fl::event_y();
18
+
19
+    if(Fl::event_y() > h() - (border * 2))
20
+      yPos = h() - (border * 2);
21
+
22
+    if(Fl::event_y() < y() + (border * 2))
23
+      yPos = y() + (border * 2);
24
+
25
+    fl_line( x() + border, yPos - 1, x() + w() - (border*2), yPos - 1 );
26
+    fl_line( x() + border, yPos    , x() + w() - (border*2), yPos     );
27
+    fl_line( x() + border, yPos + 1, x() + w() - (border*2), yPos + 1 );
28
+
29
+    /*
30
+    fl_line(
31
+      x() + border,
32
+      yPos,
33
+      x() + w() - (border*2),
34
+      yPos );
35
+
36
+    fl_line(
37
+      x() + border,
38
+      yPos + 1,
39
+      x() + w() - (border*2),
40
+      yPos + 1 );
41
+    */  
42
+
43
+    fl_pop_clip();
44
+  }
45
+  else
46
+  {
47
+    fl_push_clip(x(), y(), w(), h());
48
+    fl_pop_clip();
49
+  }
50
+
51
+  fl_color(c);
52
+  fl_line_style(0);
53
+}
54
+
55
+int Fl_HSplitter::handle(int e)
56
+{
57
+  int ret = Fl_Group::handle(e);
58
+
59
+  switch(e)
60
+  {
61
+    case FL_MOVE:
62
+
63
+      if(hCtnl - border < Fl::event_y() && Fl::event_y() < hCtnl + border)
64
+      {
65
+        fl_cursor(FL_CURSOR_NS);
66
+        splitFl = true;
67
+      }
68
+      else
69
+      {
70
+        fl_cursor(FL_CURSOR_DEFAULT);
71
+        splitFl = false;
72
+      }
73
+
74
+      return 1;
75
+
76
+    case FL_PUSH:
77
+
78
+      if(Fl::event_button() == FL_LEFT_MOUSE && splitFl)
79
+      {
80
+        redraw();
81
+      }
82
+
83
+      return 1;
84
+
85
+    case FL_RELEASE:
86
+
87
+      if(Fl::event_button() == FL_LEFT_MOUSE && splitFl)
88
+      {
89
+        c0->resize(x(), y(), w(), yPos - y());
90
+        hCtnl = yPos;
91
+        c1->resize(x(),hCtnl, w(), h() - (yPos - y()));
92
+        
93
+        if( stretchTopFl )
94
+          init_sizes();
95
+
96
+        splitFl = false;
97
+        redraw();
98
+      }
99
+
100
+      return 1;
101
+
102
+    case FL_DRAG:
103
+
104
+      if(splitFl && Fl::event_state(FL_BUTTON1) != 0)
105
+        redraw();
106
+
107
+      return 1;
108
+  }
109
+
110
+  return(ret);
111
+}
112
+
113
+
114
+Fl_HSplitter::Fl_HSplitter(int x, int y, int w, int h, int h1, const char *l, bool stretchBotFl)
115
+  : Fl_Group(x, y, w, h, l)
116
+{
117
+  int h2 = h - h1;
118
+
119
+  begin();
120
+  c0 = new Splitter_Container(x, y, w, h1);
121
+  //c0->color((Fl_Color) FL_RED);
122
+  end();
123
+
124
+  begin();
125
+  c1 = new Splitter_Container(x, y + h1, w, h2);
126
+  //c1->color((Fl_Color) FL_BLUE);
127
+  end();
128
+
129
+  hCtnl        =  y + h1;
130
+  splitFl       = false;
131
+  stretchTopFl = !stretchBotFl;
132
+  border        = Fl::box_dy(FL_DOWN_BOX);
133
+
134
+  if( stretchTopFl )
135
+    resizable(c0);
136
+}
137
+
138
+void Fl_HSplitter::resize(int x, int y, int w, int h)
139
+{
140
+  Fl_Group::resize(x, y, w, h);
141
+
142
+  if( stretchTopFl )
143
+  {
144
+    hCtnl  = c0->h() + y;
145
+    yPos   = hCtnl;
146
+    //printf("hCtnl:%i\n",hCtnl);
147
+  }
148
+  else
149
+  {
150
+    c0->resize(x, y,     w,     hCtnl - y);
151
+    c1->resize(x, hCtnl, w, h - (hCtnl - y));
152
+  }
153
+
154
+}
155
+
156
+
157
+
158
+void Fl_VSplitter::draw()
159
+{
160
+  Fl_Group::draw();
161
+  Fl_Color c = fl_color();
162
+  fl_color(FL_BLACK);
163
+  fl_line_style( FL_DOT, 1);
164
+
165
+  if(splitFl && Fl::event_button1() != 0)
166
+  {
167
+    fl_push_clip(x(), y(), w(), h());
168
+
169
+    xPos = Fl::event_x();
170
+
171
+    if(Fl::event_x() > w() - (border * 2))
172
+      xPos = w() - (border * 2);
173
+
174
+    if(Fl::event_x() < x() + (border * 2))
175
+      xPos = x() + (border * 2);
176
+
177
+    fl_line(xPos - 1, y() + border, xPos - 1, y() + h() - (border * 2));
178
+    fl_line(xPos, y() + border, xPos, y() + h() - (border * 2));
179
+    fl_line(xPos + 1, y() + border, xPos + 1, y() + h() - (border * 2));
180
+
181
+    fl_pop_clip();
182
+  }
183
+  else
184
+  {
185
+    fl_push_clip(x(), y(), w(), h());
186
+    fl_pop_clip();
187
+  }
188
+
189
+  fl_color(c);
190
+  fl_line_style(0); // restore line style to defaults
191
+}
192
+
193
+int Fl_VSplitter::handle(int e)
194
+{
195
+  int ret = Fl_Group::handle(e);
196
+
197
+  switch(e)
198
+  {
199
+    case FL_MOVE:
200
+
201
+      if(Fl::event_x() > wCtn1 - border && Fl::event_x() < wCtn1 + border)
202
+      {
203
+        fl_cursor(FL_CURSOR_WE);
204
+        splitFl = true;
205
+      }
206
+      else
207
+      {
208
+        fl_cursor(FL_CURSOR_DEFAULT);
209
+        splitFl = false;
210
+      }
211
+
212
+      return 1;
213
+
214
+    case FL_PUSH:
215
+
216
+      if(Fl::event_button() == FL_LEFT_MOUSE && splitFl)
217
+      {
218
+        redraw();
219
+      }
220
+
221
+      return 1;
222
+
223
+    case FL_RELEASE:
224
+
225
+      if(Fl::event_button() == FL_LEFT_MOUSE && splitFl)
226
+      {
227
+        c0->resize(x(), y(), xPos, h());
228
+        wCtn1 = xPos;
229
+        c1->resize(wCtn1, y(), w() - wCtn1, h());
230
+        splitFl = false;
231
+        redraw();
232
+      }
233
+
234
+      return 1;
235
+
236
+    case FL_DRAG:
237
+
238
+      if(splitFl && Fl::event_state(FL_BUTTON1) != 0)
239
+        redraw();
240
+
241
+      return 1;
242
+  }
243
+
244
+  return(ret);
245
+}
246
+
247
+Fl_VSplitter::Fl_VSplitter(int x, int y, int w, int h, const char *l)
248
+  : Fl_Group(x, y, w, h, l)
249
+{
250
+  begin();
251
+  c0 = new Splitter_Container(x, y, w / 2, h);
252
+  //c0->color((Fl_Color) FL_RED);
253
+  end();
254
+
255
+  begin();
256
+  c1 = new Splitter_Container(x + (w / 2), y, w / 2, h);
257
+  //c1->color((Fl_Color) FL_BLUE);
258
+  end();
259
+
260
+  wCtn1 = w / 2;
261
+  splitFl = false;
262
+
263
+  border = Fl::box_dx(FL_DOWN_BOX);
264
+
265
+}
266
+
267
+void Fl_VSplitter::resize_splitter(int x, int y, int w, int h)
268
+{
269
+  resize(x, y, w, h);
270
+  c0->resize(x, y, wCtn1, h);
271
+  c1->resize(wCtn1, y, w - wCtn1, h);
272
+}
273
+

+ 70
- 0
src/libcmpp/fltk/Fl_Splitter.h View File

@@ -0,0 +1,70 @@
1
+// Code based on: http://www.mail-archive.com/fltk@easysw.com/msg04573.html
2
+// Lucas Sanner/Ian MacArthur
3
+
4
+#ifndef Fl_Splitter_h
5
+#define Fl_Splitter_h
6
+
7
+#include <FL/Fl.H>
8
+#include <FL/Fl_Group.H>
9
+#include <FL/Fl_Box.H>
10
+#include <FL/fl_draw.H>
11
+
12
+
13
+class Splitter_Container : public Fl_Group
14
+{
15
+
16
+  public:
17
+
18
+    Splitter_Container(int x, int y, int w, int h, char *l = NULL)
19
+    : Fl_Group(x, y, w, h, l)
20
+    {
21
+      box(FL_NO_BOX); // do not draw the background
22
+    }
23
+};
24
+
25
+class Fl_HSplitter : public Fl_Group
26
+{
27
+  int  hCtnl;    // window coord's of the horzontal splitter 
28
+  int  border;   // splitter divider height
29
+  int  yPos;     // window posn where divider was last draw 
30
+  bool splitFl;  // set if split cursor is enabled
31
+  bool stretchTopFl;  // set to make top container stretch when splitter is resized
32
+  //int  hh2;
33
+
34
+  virtual void draw();
35
+
36
+  int handle(int e);
37
+
38
+  public:
39
+
40
+  Splitter_Container *c0, *c1;
41
+
42
+  Fl_HSplitter(int x, int y, int w, int h, int h1, const char *l=NULL, bool stretchBotFl=false);
43
+
44
+  virtual void resize(int x, int y, int w, int h);
45
+
46
+};
47
+
48
+
49
+class Fl_VSplitter : public Fl_Group
50
+{
51
+
52
+  int wCtn1, border, xPos;
53
+  bool splitFl;
54
+
55
+  void draw();
56
+  int handle(int e);
57
+
58
+  public:
59
+
60
+  Splitter_Container *c0, *c1;
61
+
62
+  Fl_VSplitter(int x, int y, int w, int h, const char *l = NULL);
63
+
64
+  void resize_splitter(int x, int y, int w, int h);
65
+
66
+
67
+
68
+};
69
+
70
+#endif

+ 66
- 0
src/libcmpp/fltk/Fl_Vert_Progress.cpp View File

@@ -0,0 +1,66 @@
1
+#include <FL/Fl.H>
2
+#include <FL/fl_draw.H>
3
+#include <Fl/Fl_Progress.H>
4
+#include "Fl_Vert_Progress.h"
5
+
6
+Fl_Vert_Progress::Fl_Vert_Progress(int x, int y, int w, int h, const char* l)
7
+  : Fl_Progress(x,y,w,h)
8
+{
9
+}
10
+
11
+// This member function is a slight variation on a verbatim
12
+// copy of Fl_Progress.cxx from the FLTK source library.
13
+void Fl_Vert_Progress::draw()
14
+{
15
+  int	progress;                 // Size of progress bar...
16
+  int	bx, by, bw, bh;           // Box areas...
17
+  int	tx, tw;                   // Temporary X + width
18
+
19
+  // Get the box borders...
20
+  bx = Fl::box_dx(box());
21
+  by = Fl::box_dy(box());
22
+  bw = Fl::box_dw(box());
23
+  bh = Fl::box_dh(box());
24
+
25
+  tx = x() + bx;
26
+  tw = w() - bw;
27
+
28
+  // Draw the progress bar...
29
+  if (maximum() > minimum())
30
+    progress = (int)(h() * (value() - minimum()) / (maximum() - minimum()) + 0.5f);
31
+  else
32
+    progress = 0;
33
+
34
+  // Draw the box and label...
35
+  if (progress > 0) 
36
+  {
37
+    Fl_Color c = labelcolor();
38
+    labelcolor(fl_contrast(labelcolor(), selection_color()));
39
+
40
+    fl_push_clip(x(), y() + h() - (progress + by), w(), progress + by);
41
+
42
+    draw_box(box(), x(), y(), w(), h(), active_r() ? selection_color() : fl_inactive(selection_color()));
43
+
44
+    draw_label(tx, y() + by, tw, h() - bh);
45
+
46
+    fl_pop_clip();
47
+
48
+    labelcolor(c);
49
+
50
+    if (progress<h()) 
51
+    {
52
+      fl_push_clip(x(), y(), w(), h()-progress);
53
+
54
+      draw_box(box(), x(), y(), w(), h(), active_r() ? color() : fl_inactive(color()));
55
+
56
+      draw_label(tx, y() + by, tw, h() - bh);
57
+
58
+      fl_pop_clip();
59
+    }
60
+  } 
61
+  else 
62
+  {
63
+    draw_box(box(), x(), y(), w(), h(), active_r() ? color() : fl_inactive(color()));
64
+    draw_label(tx, y() + by, tw, h() - bh);
65
+  }
66
+}

+ 14
- 0
src/libcmpp/fltk/Fl_Vert_Progress.h View File

@@ -0,0 +1,14 @@
1
+#ifndef Fl_Vert_Progress_h
2
+#define Fl_Vert_Progress_h
3
+
4
+class Fl_Vert_Progress : public Fl_Progress
5
+{
6
+ protected:
7
+  virtual void draw();
8
+ public:
9
+  Fl_Vert_Progress(int x, int y, int w, int h, const char* l=0);
10
+  
11
+};
12
+
13
+
14
+#endif

+ 1546
- 0
src/libcmpp/fltk/cmGrFltk.cpp
File diff suppressed because it is too large
View File


+ 242
- 0
src/libcmpp/fltk/cmGrFltk.h View File

@@ -0,0 +1,242 @@
1
+#ifndef cmGrFltk_h
2
+#define cmGrFltk_h
3
+
4
+class Fl_Group;
5
+class Fl_Output;
6
+class Fl_Scrollbar;
7
+
8
+class cmGrDevDrvFltk
9
+{
10
+ public:
11
+
12
+  cmGrDevDrvFltk();
13
+  virtual ~cmGrDevDrvFltk(){}
14
+
15
+
16
+  static bool     create( void* user, unsigned w, unsigned h );
17
+  static void     destroy( void* user );
18
+
19
+  static void     begin_draw( void* arg );
20
+  static void     end_draw(   void* arg );
21
+  static void     draw(       void* arg, int x, int y );
22
+
23
+  static void     set_color( void* user, const cmGrColor_t  c );  
24
+  static void     get_color( void* user,       cmGrColor_t* c );  
25
+
26
+  static void     set_font_family( void* user, unsigned fontId );
27
+  static unsigned get_font_family( void* user );
28
+
29
+  static void     set_font_style( void* user, unsigned style );
30
+  static unsigned get_font_style( void* user );
31
+
32
+  static void     set_font_size( void* user, unsigned size );
33
+  static unsigned get_font_size( void* user );
34
+
35
+  static void     set_pen_style( void* user, unsigned styleFlags );
36
+  static unsigned get_pen_style( void* user );
37
+
38
+  static void     set_pen_width( void* user, unsigned w );  
39
+  static unsigned get_pen_width( void* user );
40
+
41
+  static void draw_line(     void* user, int x0, int y0, int x1, int y1 );
42
+  static void draw_rect(     void* user, int x0, int y0, unsigned w, unsigned h );
43
+  static void fill_rect(     void* user, int x0, int y0, unsigned w, unsigned h );
44
+  static void draw_ellipse(  void* user, int x0, int y0, unsigned w, unsigned h );
45
+  static void fill_ellipse(  void* user, int x0, int y0, unsigned w, unsigned h );
46
+  static void draw_diamond(  void* user, int x0, int y0, unsigned w, unsigned h );
47
+  static void fill_diamond(  void* user, int x0, int y0, unsigned w, unsigned h );
48
+  static void draw_triangle( void* user, int x0, int y0, unsigned w, unsigned h, unsigned dirFlag );
49
+  static void fill_triangle( void* user, int x0, int y0, unsigned w, unsigned h, unsigned dirFlag );
50
+
51
+  static void draw_text(     void* user, const char* text, int x, int y );
52
+  static void draw_text_rot( void* user, const char* text, int x, int y, int angle );
53
+  static void measure_text(  void* user, const char* text, unsigned* w, unsigned* h );
54
+
55
+  static void read_image( void* user,       unsigned char* p, int x, int y, unsigned w, unsigned h );
56
+  static void draw_image( void* user, const unsigned char* p, int x, int y, unsigned w, unsigned h );
57
+
58
+  bool is_initialized() const;
59
+
60
+  cmGrDev_t    d;
61
+
62
+ private:  
63
+
64
+  unsigned _fltk_pen_width;
65
+  unsigned _fltk_pen_style; 
66
+  unsigned _fltk_font_size;
67
+  unsigned _w;
68
+  unsigned _h;
69
+
70
+  static void _get_font_family_style(             unsigned* fontId, unsigned* style );
71
+  static void _set_font_family_style( void* user, unsigned  fontId, unsigned  style );
72
+};
73
+
74
+//--------------------------------------------------------------------------------------
75
+// Canvas Object 
76
+
77
+class cmGrViewFltk : public Fl_Widget
78
+{
79
+ public:
80
+  cmGrViewFltk( cmCtx_t* ctx, cmGrH_t grH, int x, int y, int w, int h );
81
+  virtual ~cmGrViewFltk();
82
+
83
+  virtual int  handle(int event);
84
+  virtual void resize(int x, int y, int w, int h );
85
+          void setGrH( cmGrH_t grH );
86
+
87
+ private:
88
+  virtual void draw();
89
+
90
+  typedef struct 
91
+  {
92
+    unsigned idx;
93
+    unsigned fltk_code;
94
+    char     ch;
95
+    cmGrKeyCodeId_t gr_code;
96
+  } keyMap_t;
97
+
98
+  cmGrH_t         _grH;
99
+  cmGrDevDrvFltk  _dd;
100
+  cmGrDcH_t       _dcH;
101
+  static keyMap_t _keymap[];
102
+
103
+  const keyMap_t* _getGrKeyCode( unsigned fltk_code );
104
+  cmGrKeyCodeId_t _eventKeyCode( );
105
+
106
+};
107
+
108
+
109
+//--------------------------------------------------------------------------------------
110
+// Container for multiple plots
111
+
112
+class cmGrPageFltk : public Fl_Group 
113
+{
114
+ public:
115
+  cmGrPageFltk( cmCtx_t* ctx, cmGrPgH_t pgH,  int x, int y, int w, int h );
116
+  virtual ~cmGrPageFltk();
117
+  
118
+  virtual void             createView( unsigned vwIdx );
119
+
120
+  virtual void             destroyView( unsigned vwIdx );
121
+
122
+  virtual cmGrDcH_t        devCtxHandle();
123
+
124
+  virtual cmGrViewFltk*   viewWidget( unsigned vwIdx );
125
+
126
+  virtual void resize(int x, int y, int w, int h );
127
+  
128
+ private:
129
+  virtual void draw();
130
+
131
+  cmGrDevDrvFltk _dd;
132
+  cmCtx_t*       _ctx;
133
+  cmGrPgH_t      _pgH;
134
+  cmGrDcH_t      _dcH;
135
+  cmGrViewFltk** _vwV;
136
+  unsigned       _vwN;
137
+  
138
+};
139
+
140
+//--------------------------------------------------------------------------------------
141
+// Contains a single cmGrPageFltk and a control panel
142
+
143
+class cmGrPlotFltk : public Fl_Group
144
+{
145
+ public:
146
+  cmGrPlotFltk( cmCtx_t* ctx, int x, int y, int w, int h, int rn=1, int cn=1, int textSz=10 );
147
+  virtual ~cmGrPlotFltk();
148
+
149
+  virtual void resize(int x, int y, int w, int h );
150
+
151
+  cmGrPgH_t pageHandle();
152
+  cmGrPlH_t plotHandle();
153
+  cmGrDcH_t dcHandle();
154
+
155
+  virtual void initViews( int rn, int cn );
156
+  virtual void setStatusText( const cmChar_t* s );
157
+  
158
+  virtual void on_button( unsigned id );
159
+  virtual void on_scroll( Fl_Scrollbar* sb, unsigned id );
160
+  virtual void on_view_create(   unsigned viewIdx );
161
+  virtual void on_view_destroy(  unsigned viewIdx );
162
+  virtual void rpt_local_pt(     cmGrH_t grH );
163
+  virtual void rpt_global_pt(    cmGrH_t grH );
164
+  virtual void on_phys_change(   cmGrH_t grH );
165
+  virtual void on_view_change(   cmGrH_t grH );
166
+  virtual void on_select_change( cmGrH_t grH );
167
+  virtual void on_focused_plot(  cmGrH_t grH );
168
+  virtual void on_key_event(     cmGrH_t grH, unsigned eventFlags, cmGrKeyCodeId_t keycode );
169
+  virtual bool on_plot_object(   cmGrPlotCbArg_t* arg );
170
+
171
+ private:
172
+  enum
173
+  {
174
+    kHBord = 0,     // dist between vertical elements (cols)
175
+    kVBord = 0,     // dist between horz elements (rows)
176
+    kBtnH  = 20,    // control height
177
+    kBtnW  = 50,    // button width
178
+    kOutW  = 100,   // output width
179
+    kLblW  = 20,    // output label width,
180
+    kScrD  = 20     // scroll bar thickness
181
+  };
182
+
183
+  enum
184
+  {
185
+    kHScrollId,
186
+    kVScrollId,
187
+    kShowAllId,
188
+    kReportId,
189
+    kZoomInId,
190
+    kZoomOutId,
191
+    kZoomInXId,
192
+    kZoomInYId,
193
+    kZoomOutXId,
194
+    kZoomOutYId,
195
+  };
196
+
197
+
198
+  cmGrPgH_t      _pgH;
199
+  cmGrPlH_t      _plH;
200
+  
201
+  cmGrPageFltk* _pg;
202
+  Fl_Group*     _ctl_grp;
203
+  Fl_Group*     _usr_grp;
204
+  Fl_Output*    _status;        // status text output
205
+ 
206
+  Fl_Scrollbar* _hsb;           // scroll bars
207
+  Fl_Scrollbar* _vsb;
208
+
209
+  Fl_Output*    _gx;            // current global coord display
210
+  Fl_Output*    _gy;
211
+
212
+  Fl_Output*    _lx;            // current local coord display
213
+  Fl_Output*    _ly;
214
+
215
+  Fl_Output*    _s0x;           // seletion point
216
+  Fl_Output*    _s0y;
217
+  Fl_Output*    _s1x;  
218
+  Fl_Output*    _s1y;
219
+  Fl_Output*    _sdx;
220
+  Fl_Output*    _sdy;
221
+ 
222
+  int            _textSz;
223
+
224
+  void      _layout();
225
+  Fl_Group* _create_ctls();
226
+  void      _create_scroll_bars();
227
+  void      _showHideScrollBars();
228
+  cmGrH_t   _getFocusedView();
229
+
230
+  // controls callback
231
+  static void _s_ctl_cb(Fl_Widget* w, long id );
232
+
233
+  // plot page callbacks
234
+  static void _s_cmGrCallback( void* arg, cmGrH_t grH, cmGrCbId_t id, unsigned eventFlags, cmGrKeyCodeId_t keycode );
235
+
236
+  // plot object callbacks
237
+  static bool _s_cmGrPlotObjCbFunc( cmGrPlotCbArg_t* arg );
238
+  
239
+};
240
+
241
+
242
+#endif

+ 865
- 0
src/libcmpp/fltk/cmUiDrvrFltk.cpp View File

@@ -0,0 +1,865 @@
1
+#include <FL/Fl.H>
2
+#include <FL/Fl_Widget.H>
3
+#include <FL/Fl_Group.H>
4
+#include <FL/Fl_Tabs.H>
5
+#include <FL/Fl_Button.H>
6
+#include <FL/Fl_Check_Button.H>
7
+#include <FL/Fl_Box.H>
8
+#include <Fl/Fl_Input.H>
9
+#include <Fl/Fl_Value_Input.H>
10
+#include <Fl/Fl_Value_Slider.H>
11
+#include <Fl/Fl_Progress.H>
12
+#include <Fl/Fl_Menu_Button.H>
13
+#include <Fl/Fl_Select_Browser.H>
14
+#include <Fl/Fl_Text_Display.H>
15
+#include <FL/fl_draw.H>
16
+
17
+#include "Fl_File_Btn.h"
18
+#include "Fl_Vert_Progress.h"
19
+
20
+#include "cmGlobal.h"
21
+#include "cmRpt.h"
22
+#include "cmErr.h"
23
+#include "cmCtx.h"
24
+#include "cmMem.h"
25
+#include "cmMallocDebug.h"
26
+
27
+#include "cmRtSysMsg.h"
28
+#include "cmUiDrvr.h"
29
+#include "cmUiDrvrFltk.h"
30
+
31
+
32
+cmUiDrvrFltk::cmUiDrvrFltk(cmCtx_t* ctx, Fl_Tabs* tabs, cmUiDriverFunc_t cbFunc, void* cbArg)
33
+  : _tabs(NULL),_cbFunc(NULL),_cbArgs(NULL),_panels(NULL)
34
+{
35
+  cmErrSetup(&_err,&ctx->rpt,"cmUiDrvrFltk");
36
+  setBaseWindow(tabs);
37
+  setCallback(cbFunc,cbArg);
38
+}
39
+
40
+void cmUiDrvrFltk::setBaseWindow( Fl_Tabs* tabs )
41
+{ 
42
+  _tabs  = tabs; 
43
+  if( _tabs != NULL )
44
+    _tabs->callback(_s_tab_cb,this);
45
+}
46
+
47
+void cmUiDrvrFltk::setCallback( cmUiDriverFunc_t cbFunc, void* cbArg )
48
+{
49
+  _cbFunc = cbFunc;
50
+  _cbArgs = cbArg;  
51
+}
52
+
53
+cmUiDrvrFltk::~cmUiDrvrFltk()
54
+{ 
55
+  _destroyAllPanels(false); 
56
+}
57
+  
58
+cmUiRC_t cmUiDrvrFltk::cmUiDriverFunc( void* cbArg, const cmUiDriverArg_t* args )
59
+{
60
+  cmUiDrvrFltk* p = (cmUiDrvrFltk*)cbArg;
61
+  cmUiRC_t rc = kOkUiRC;
62
+  switch(args->dId)
63
+  {
64
+    case kInvalidDId:
65
+      break;
66
+
67
+    case kCreateCtlDId:
68
+      rc = p->_createCtl(args);
69
+      break;
70
+
71
+    case kDestroyCtlDId:
72
+      rc = p->_destroyCtl(args->appId,args->panelId,args->usrId,true);
73
+      break;
74
+
75
+    case kSetValDId:
76
+      rc = p->_setValueCtl(args);
77
+      break;
78
+
79
+    case kEnableDId:
80
+      rc = p->_enableCtl(args);
81
+      break;
82
+
83
+      //case kDestroyAllDId:
84
+      //rc = p->_destroyAllPanels(true);
85
+      //break;
86
+
87
+    case kMaxDId:
88
+      assert(0);
89
+      break;
90
+      
91
+  }
92
+  return rc;
93
+}
94
+
95
+void cmUiDrvrFltk::_insertNewCtl( panel_t* pp, ctl_t* ctl, Fl_Widget* wp, unsigned flags )
96
+{
97
+  ctl->wdgt = wp;
98
+
99
+  if( ctl->usrId != cmInvalidId )
100
+  {
101
+    ctl->link = pp->ctls;
102
+    pp->ctls  = ctl;
103
+    wp->callback( _s_ctl_cb, ctl );
104
+  }
105
+
106
+  pp->grp->add(wp);
107
+  
108
+
109
+  int align_flags = 0;
110
+  if( cmIsFlag(flags,kLeftUiFl))   align_flags |= FL_ALIGN_LEFT; 
111
+  if( cmIsFlag(flags,kTopUiFl))    align_flags |= FL_ALIGN_TOP; 
112
+  if( cmIsFlag(flags,kRightUiFl))  align_flags |= FL_ALIGN_RIGHT; 
113
+  if( cmIsFlag(flags,kBottomUiFl)) align_flags |= FL_ALIGN_BOTTOM; 
114
+  if( cmIsFlag(flags,kHCtrUiFl))   align_flags |= FL_ALIGN_CENTER; 
115
+  if( cmIsFlag(flags,kInsideUiFl)) align_flags |= FL_ALIGN_INSIDE; 
116
+  if( cmIsFlag(flags,kVCtrUiFl))   align_flags =  cmClrFlag(align_flags,FL_ALIGN_TOP | FL_ALIGN_BOTTOM); 
117
+
118
+
119
+  wp->align(align_flags);
120
+
121
+
122
+  int when_flags = 0;
123
+  if( cmIsFlag(flags,kSendChangeFl))   when_flags |= FL_WHEN_CHANGED;
124
+  if( cmIsFlag(flags,kSendEnterFl))    when_flags |= FL_WHEN_ENTER_KEY;
125
+  if( cmIsFlag(flags,kSendFocusFl))    when_flags |= FL_WHEN_RELEASE;
126
+  if( cmIsFlag(flags,kSendNoChangeFl)) when_flags |= FL_WHEN_NOT_CHANGED;
127
+    
128
+  if( when_flags != 0 )
129
+    wp->when(when_flags);
130
+}
131
+
132
+bool cmUiDrvrFltk::_hasNoAlignFlags( unsigned flags ) const
133
+{ 
134
+  return !cmIsFlag(flags, kLeftUiFl | kTopUiFl | kRightUiFl | kBottomUiFl | kVCtrUiFl | kHCtrUiFl );
135
+}
136
+
137
+cmUiRC_t cmUiDrvrFltk::_createCtl( const cmUiDriverArg_t* a )
138
+{
139
+  cmUiRC_t rc;
140
+  panel_t* pp;
141
+  panel_t* prvPnl;
142
+
143
+  // if this is a panel create request
144
+  if( a->cId == kPanelUiCId  )
145
+    return _createPanel(a);
146
+
147
+  // locate the new control's panel
148
+  if((rc = _findPanel(a->appId,a->panelId,pp,prvPnl)) != kOkUiRC )
149
+    return rc;
150
+
151
+  // allocate the control record
152
+  ctl_t* ctl ;
153
+  if( a->usrId == cmInvalidId )
154
+    ctl = &_dummy;
155
+  else
156
+    ctl = cmMemAllocZ(ctl_t,1);
157
+
158
+  ctl->cId   = a->cId;
159
+  ctl->pnl   = pp;
160
+  ctl->usrId = a->usrId;
161
+  ctl->flags = a->flags;
162
+
163
+  int x = a->x + pp->x_offs;
164
+  int y = a->y + pp->y_offs;
165
+
166
+  // cache the event callback arg record so that it 
167
+  // does not have to be filled on every callback.
168
+  cmUiDriverArgSetup(&ctl->cbArg,a->hdr.rtSubIdx,kUiDrvrSelRtId,kInvalidDId,pp->appId,a->usrId,pp->usrId,a->cId,0,0,0,NULL,x,y,a->w,a->h);
169
+
170
+  //printf("%i %i %i %i\n",x,y,a->w,a->h);
171
+
172
+  switch(a->cId)
173
+  {
174
+    case kInvalidUiCId:
175
+      assert(0);
176
+      break;
177
+
178
+    case kPanelUiCId:
179
+      break;
180
+
181
+    case kBtnUiCId:
182
+      ctl->u.btn = new Fl_Button(x,y,a->w,a->h,a->sval);
183
+      _insertNewCtl(pp,ctl,ctl->u.btn,a->flags);
184
+      ctl->cbArg.flags |= kIvalUiFl;
185
+      break;
186
+
187
+    case kCheckUiCId:
188
+      ctl->u.chk = new Fl_Check_Button(x,y,a->w,a->h,a->sval);
189
+      _insertNewCtl(pp,ctl,ctl->u.chk,a->flags);
190
+      ctl->cbArg.flags |= kIvalUiFl;
191
+      ctl->u.chk->value(a->ival);
192
+      break;
193
+
194
+    case kMenuBtnUiCId:
195
+      ctl->u.mbt = new Fl_Menu_Button(x,y,a->w,a->h,a->sval!=NULL ? a->sval : NULL);
196
+      _insertNewCtl(pp,ctl,ctl->u.mbt,a->flags);
197
+      ctl->cbArg.flags |= kIvalUiFl;
198
+      ctl->u.mbt->value(0);
199
+      break;
200
+
201
+    case kListUiCId:
202
+      ctl->u.lst = new Fl_Select_Browser(x,y,a->w,a->h);      
203
+      _insertNewCtl(pp,ctl,ctl->u.lst,a->flags);
204
+      ctl->cbArg.flags |= kIvalUiFl;
205
+      break;
206
+
207
+    case kLabelUiCId:
208
+      {
209
+        unsigned flags = a->flags;
210
+        ctl->u.lbl = new Fl_Box(x,y,a->w,a->h);
211
+        ctl->u.lbl->copy_label(a->sval);
212
+        if( _hasNoAlignFlags(flags) )
213
+          flags |= kHCtrUiFl | kInsideUiFl;
214
+        _insertNewCtl(pp,ctl,ctl->u.lbl,flags);
215
+      }
216
+      break;
217
+
218
+    case kStringUiCId:
219
+      {
220
+        unsigned flags = a->flags;
221
+        ctl->u.str = new Fl_Input(x,y,a->w/2,a->h);
222
+        ctl->u.str->copy_label(a->sval);
223
+        if( _hasNoAlignFlags(flags) )
224
+          flags |= kRightUiFl;
225
+        _insertNewCtl(pp,ctl,ctl->u.str,flags);
226
+        ctl->cbArg.flags |= kSvalUiFl;
227
+      }
228
+      break;
229
+
230
+    case kConsoleUiCId:
231
+      {
232
+        unsigned flags = a->flags;
233
+        ctl->u.con = new Fl_Text_Display(x,y,a->w,a->h);
234
+        ctl->u.con->buffer(new Fl_Text_Buffer());
235
+        ctl->u.con->textsize(12);
236
+        ctl->u.con->textfont(FL_COURIER);
237
+        ctl->u.con->copy_label(a->sval);
238
+        if( _hasNoAlignFlags(flags) )
239
+          flags |= kRightUiFl;
240
+        _insertNewCtl(pp,ctl,ctl->u.con,flags);
241
+        ctl->cbArg.flags |= kSvalUiFl;
242
+      }
243
+      break;
244
+
245
+    case kSliderUiCId:
246
+      {
247
+        unsigned flags = a->flags;
248
+        int      w = a->w;
249
+        int      h = a->h;
250
+
251
+        if( cmIsFlag(flags,kHorzUiFl) )
252
+        {
253
+          if( _hasNoAlignFlags(flags) )
254
+            flags |= kRightUiFl;
255
+
256
+          w /= 2;
257
+
258
+        }
259
+
260
+        if( cmIsFlag(flags,kVertUiFl) )
261
+        {
262
+          if( _hasNoAlignFlags(flags) )
263
+            flags |= kTopUiFl | kHCtrUiFl;
264
+
265
+          if( a->sval != NULL )
266
+          {
267
+            int hh,ww;
268
+            fl_measure(a->sval,ww,hh);
269
+
270
+            if( flags & kTopUiFl )
271
+            {
272
+              y += hh;
273
+              h -= hh;
274
+            }
275
+        
276
+            if( flags & kBottomUiFl)
277
+              h -= hh;
278
+
279
+          }
280
+        }
281
+
282
+        ctl->u.sld = new Fl_Value_Slider(x,y,w,h);
283
+        ctl->u.sld->copy_label(a->sval);
284
+
285
+
286
+        if( cmIsFlag(flags,kHorzUiFl) )
287
+          ctl->u.sld->type(FL_HOR_NICE_SLIDER);
288
+
289
+        if( cmIsFlag(flags,kVertUiFl) )
290
+          ctl->u.sld->type(FL_VERT_NICE_SLIDER);
291
+
292
+        _insertNewCtl(pp,ctl,ctl->u.sld,flags);
293
+
294
+        ctl->cbArg.flags |= kFvalUiFl;
295
+
296
+      }
297
+      break;
298
+
299
+    case kNumberUiCId:
300
+      {
301
+        unsigned flags = a->flags;
302
+        ctl->u.num = new Fl_Value_Input(x,y,a->w/2,a->h);
303
+        ctl->u.num->copy_label(a->sval);
304
+        if( _hasNoAlignFlags(flags) )
305
+          flags |= kRightUiFl;
306
+
307
+        _insertNewCtl(pp,ctl,ctl->u.num,flags);
308
+        ctl->cbArg.flags |= kFvalUiFl;
309
+        ctl->u.num->when(FL_WHEN_ENTER_KEY | FL_WHEN_NOT_CHANGED ); 
310
+      }
311
+      break;
312
+
313
+    case kProgressUiCId:
314
+      {
315
+        unsigned flags = a->flags;
316
+        ctl->u.prg = new Fl_Progress(x,y,a->w/2,a->h);
317
+        ctl->u.prg->copy_label(a->sval);
318
+        if( _hasNoAlignFlags(flags) )
319
+          flags |= kRightUiFl;
320
+        _insertNewCtl(pp,ctl,ctl->u.prg,flags);
321
+        ctl->u.prg->color( fl_rgb_color((unsigned char)256),fl_rgb_color((unsigned char)128));
322
+      }
323
+      break;
324
+
325
+    case kMeterUiCId:
326
+      {
327
+        unsigned flags = a->flags;
328
+        if( cmIsFlag(flags,kVertUiFl) )
329
+        {
330
+          ctl->u.mtr = new Fl_Vert_Progress(x,y,a->w/2,a->h);
331
+          ctl->u.mtr->color( fl_rgb_color((unsigned char)256),fl_rgb_color((unsigned char)128));
332
+        }
333
+        else
334
+        {
335
+          ctl->u.mtr = new Fl_Progress(x,y,a->w,a->h);
336
+          ctl->u.mtr->color( fl_rgb_color((unsigned char)256),fl_rgb_color((unsigned char)128));
337
+        }
338
+
339
+        ctl->u.mtr->copy_label(a->sval);
340
+
341
+        if( _hasNoAlignFlags(flags) )
342
+          flags |= kRightUiFl;
343
+        _insertNewCtl(pp,ctl,ctl->u.mtr,flags);
344
+      }
345
+      break;
346
+
347
+    case kFilenameUiCId:
348
+    case kDirUiCId:
349
+      {
350
+        unsigned flags = a->cId==kDirUiCId ? Fl_File_Btn::kDir_Type_Id : Fl_File_Btn::kFile_Type_Id;
351
+        ctl->u.fnb = new Fl_File_Btn(flags,"",x,y,a->w,a->h,a->sval);
352
+        flags = a->flags;
353
+        if( _hasNoAlignFlags(flags) )
354
+          flags |= kRightUiFl;
355
+        _insertNewCtl(pp,ctl,ctl->u.fnb,flags);
356
+        ctl->cbArg.flags |= kSvalUiFl;
357
+      }
358
+      break;
359
+
360
+    case kMaxUiCId:
361
+      assert(0);
362
+      break;
363
+
364
+  }
365
+
366
+  pp->grp->redraw();
367
+
368
+  return rc;
369
+}
370
+
371
+cmUiRC_t cmUiDrvrFltk::_setValueCtl( const cmUiDriverArg_t* a )
372
+{
373
+  cmUiRC_t rc;
374
+  panel_t* pp     = NULL;
375
+  panel_t* prvPnl = NULL;
376
+  ctl_t*   ctl    = NULL;
377
+  ctl_t*   prvCtl = NULL;
378
+
379
+  if((rc = _findPanel(a->appId,a->panelId,pp,prvPnl)) != kOkUiRC )
380
+    return rc;
381
+
382
+  if((rc= _findCtl(pp, a->usrId, ctl, prvCtl )) != kOkUiRC )
383
+    return rc;
384
+
385
+
386
+  switch( a->cId )
387
+  {
388
+    case kInvalidUiCId:
389
+      break;
390
+
391
+    case kPanelUiCId:
392
+      break;
393
+
394
+    case kBtnUiCId:
395
+      if( cmIsFlag(a->flags,kLblUiFl) )
396
+        ctl->u.btn->copy_label(a->sval);
397
+      break;
398
+
399
+    case kCheckUiCId:
400
+      switch( a->flags & (kLblUiFl | kValUiFl) )
401
+      {
402
+        case kValUiFl: ctl->u.chk->value(a->ival); break;
403
+        case kLblUiFl: ctl->u.chk->copy_label(a->sval); break;
404
+      }
405
+      break;
406
+
407
+    case kMenuBtnUiCId:
408
+      switch( a->flags & (kAppendUiFl | kClearUiFl | kValUiFl) )
409
+      {
410
+        case kValUiFl: 
411
+          if( a->ival < ctl->u.mbt->size() )
412
+          {
413
+            ctl->u.mbt->value(a->ival); 
414
+            if( ctl->u.mbt->mvalue() != NULL)
415
+              ctl->u.mbt->copy_label( ctl->u.mbt->mvalue()->label());
416
+          }
417
+          break;
418
+
419
+        case kClearUiFl: 
420
+          ctl->u.mbt->clear(); 
421
+          ctl->u.mbt->copy_label("");
422
+          break;
423
+
424
+        case kAppendUiFl: 
425
+          {
426
+            int n;
427
+            ctl->u.mbt->add( a->sval,0,ctl->u.mbt->callback(),ctl->u.mbt->user_data(),0); 
428
+            n = ctl->u.mbt->size();
429
+            if( (n) == 2 )
430
+            {
431
+              
432
+              ctl->u.mbt->value(0);
433
+              if( ctl->u.mbt->mvalue() != NULL)
434
+              {
435
+                const char* s = ctl->u.mbt->mvalue()->label();
436
+                ctl->u.mbt->copy_label( s);
437
+              }
438
+            }
439
+          }
440
+          break;
441
+      }
442
+      break;
443
+
444
+    case kListUiCId:
445
+      switch( a->flags & (kAppendUiFl | kClearUiFl | kValUiFl) )
446
+      {
447
+        case kValUiFl:    ctl->u.lst->value(a->ival);  break;
448
+        case kAppendUiFl: ctl->u.lst->add( a->sval ); break;
449
+        case kClearUiFl:  ctl->u.lst->clear(); break;
450
+      }
451
+      break;
452
+
453
+    case kLabelUiCId:
454
+      ctl->u.str->value(a->sval); 
455
+      break;
456
+
457
+    case kStringUiCId:
458
+      switch( a->flags & (kLblUiFl | kValUiFl) )
459
+      {
460
+        case kValUiFl: ctl->u.str->value(a->sval); break;
461
+        case kLblUiFl: ctl->u.str->copy_label(a->sval); break;
462
+      }
463
+      break;
464
+
465
+    case kConsoleUiCId:
466
+      switch( a->flags & (kLblUiFl | kValUiFl) )
467
+      {
468
+        case kValUiFl: if(a->sval!=NULL) ctl->u.con->insert(a->sval); break;
469
+        case kLblUiFl: ctl->u.str->copy_label(a->sval); break;
470
+      }
471
+      break;
472
+
473
+    case kSliderUiCId:
474
+    case kNumberUiCId:
475
+      {
476
+        Fl_Valuator* vp = static_cast<Fl_Valuator*>(ctl->wdgt);
477
+
478
+        // Correct for problem where the vertical slider values go up as the
479
+        // slider knob is dragged down.
480
+        bool invertFl =  a->cId == kSliderUiCId && cmIsFlag(ctl->flags,kVertUiFl);
481
+
482
+        switch(a->flags & (kNumMask | kLblUiFl | kMinUiFl | kMaxUiFl))
483
+        {
484
+          case kLblUiFl: ctl->u.num->copy_label(a->sval); break;
485
+          case kValUiFl: vp->value(a->fval);   break;
486
+          case kIncUiFl: vp->step(a->fval);    break;
487
+          case kMinUiFl: invertFl ? vp->maximum(a->fval) : vp->minimum(a->fval); break;
488
+          case kMaxUiFl: invertFl ? vp->minimum(a->fval) : vp->maximum(a->fval); break;
489
+        }
490
+      }
491
+      break;
492
+
493
+    case kProgressUiCId:
494
+      switch( a->flags & (kLblUiFl | kValUiFl | kMinUiFl | kMaxUiFl) )
495
+      {
496
+        case kValUiFl: ctl->u.prg->value(a->ival); break;
497
+        case kLblUiFl: ctl->u.prg->copy_label(a->sval); break;
498
+        case kMinUiFl: ctl->u.prg->minimum(a->ival); break;
499
+        case kMaxUiFl: ctl->u.prg->maximum(a->ival); break;
500
+      }
501
+      break;
502
+
503
+    case kMeterUiCId:
504
+      switch( a->flags & (kLblUiFl | kValUiFl | kMinUiFl | kMaxUiFl) )
505
+      {
506
+        case kValUiFl: ctl->u.mtr->value(a->ival); ctl->u.mtr->redraw(); break;
507
+        case kLblUiFl: ctl->u.mtr->copy_label(a->sval); break;
508
+        case kMinUiFl: ctl->u.prg->minimum(a->ival); break;
509
+        case kMaxUiFl: ctl->u.prg->maximum(a->ival); break;
510
+      }
511
+      break;
512
+
513
+    case kFilenameUiCId:
514
+    case kDirUiCId:
515
+      switch(a->flags & (kFnMask | kValUiFl | kFnPatUiFl | kFnDirUiFl) )
516
+      {
517
+        case kValUiFl:   
518
+          ctl->u.fnb->filename(a->sval); 
519
+          break;
520
+        case kFnPatUiFl: ctl->u.fnb->pattern_string(a->sval); break;
521
+        case kFnDirUiFl: 
522
+          ctl->u.fnb->type( ctl->u.fnb->type()==Fl_File_Btn::kFile_Type_Id ? Fl_File_Btn::kDir_Type_Id : Fl_File_Btn::kFile_Type_Id );
523
+          break;
524
+      }
525
+      break;
526
+
527
+    case kMaxUiCId:
528
+      assert(0);
529
+      break;
530
+  }
531
+
532
+  // echo the result back to the UI
533
+  //if( cmIsFlag(a->flags,kValUiFl|kAppendUiFl) )
534
+  //  _cbFunc(_cbArgs,a);
535
+
536
+  return rc;
537
+}
538
+
539
+cmUiRC_t cmUiDrvrFltk::_enableCtl( const cmUiDriverArg_t* a )
540
+{
541
+  cmUiRC_t rc;
542
+  panel_t* pp     = NULL;
543
+  panel_t* prvPnl = NULL;
544
+  ctl_t*   ctl    = NULL;
545
+  ctl_t*   prvCtl = NULL;
546
+
547
+  if((rc = _findPanel(a->appId,a->panelId,pp,prvPnl)) != kOkUiRC )
548
+    return rc;
549
+
550
+  if((rc= _findCtl(pp, a->usrId, ctl, prvCtl )) != kOkUiRC )
551
+    return rc;
552
+
553
+  if( a->ival )
554
+    ctl->wdgt->activate();
555
+  else
556
+    ctl->wdgt->deactivate();
557
+
558
+  _doCb(ctl,kEnableDId,0);
559
+
560
+  return rc;
561
+}
562
+
563
+cmUiRC_t   cmUiDrvrFltk::_destroyCtl( unsigned appId, unsigned panelId, unsigned usrId, bool deleteWindowEleFlag )
564
+{
565
+  cmUiRC_t rc     = kOkUiRC;
566
+
567
+  panel_t* pp     = NULL;
568
+  panel_t* prvPnl = NULL;
569
+
570
+  // locate the panel assoc'd with the ctl
571
+  if((rc = _findPanel(appId,panelId,pp,prvPnl,true)) != kOkUiRC )
572
+    return rc;
573
+
574
+  // if the panel is the ctl to delete ...
575
+  if( usrId == pp->usrId )
576
+  {
577
+    // ... unlink the panel
578
+    if( prvPnl!=NULL)
579
+      prvPnl->link = pp->link;
580
+    else
581
+    {
582
+      assert(_panels == pp );
583
+      _panels = pp->link;
584
+    }
585
+  }
586
+
587
+  return _destroyCtl(pp,usrId,deleteWindowEleFlag);
588
+}
589
+
590
+cmUiRC_t   cmUiDrvrFltk::_destroyCtl( panel_t* pp, unsigned usrId, bool deleteWindowEleFlag )
591
+{
592
+  cmUiRC_t rc     = kOkUiRC;
593
+  ctl_t*   ctl    = NULL;
594
+  ctl_t*   prvCtl = NULL;
595
+
596
+  // if the panel is the ctl to delete
597
+  if( usrId == pp->usrId )
598
+  {
599
+    return _destroyPanel(pp,deleteWindowEleFlag);
600
+  }
601
+
602
+  // locate the control on the panel
603
+  if((rc = _findCtl(pp,usrId,ctl,prvCtl,true)) != kOkUiRC )
604
+    return rc;
605
+
606
+  // unlink the control
607
+  if( prvCtl!=NULL)
608
+    prvCtl->link = ctl->link;
609
+  else
610
+  {
611
+    assert( pp->ctls == ctl );
612
+    pp->ctls = ctl->link;
613
+  }
614
+  
615
+  // delete the window element
616
+  if( deleteWindowEleFlag)
617
+    delete ctl->wdgt;
618
+
619
+  // release the control recd
620
+  cmMemFree(ctl);
621
+
622
+  return rc;
623
+}
624
+
625
+cmUiRC_t cmUiDrvrFltk::_createPanel( const cmUiDriverArg_t* a )
626
+{
627
+  int tx,ty,tw,th;
628
+  _tabs->client_area(tx,ty,tw,th);
629
+  panel_t* pnl = cmMemAllocZ(panel_t,1);
630
+  
631
+  pnl->drvr   = this;
632
+  pnl->grp    = new Fl_Group(tx,ty,tw,th,a->sval);
633
+  pnl->grp->user_data(pnl);
634
+  pnl->appId  = a->appId;
635
+  pnl->usrId  = a->usrId;
636
+  pnl->x_offs = tx + 2;
637
+  pnl->y_offs = ty + 2;
638
+  pnl->link   = _panels;
639
+  _panels     = pnl;
640
+
641
+  pnl->grp->end();
642
+
643
+  if( cmIsFlag(a->flags,kPrependUiFl) )
644
+    _tabs->insert(*pnl->grp,0);
645
+  else
646
+    _tabs->add(pnl->grp);
647
+
648
+  // cache the event callback arg record so that it 
649
+  // does not have to be filled on every callback.
650
+  cmUiDriverArgSetup(&pnl->cbArg,a->hdr.rtSubIdx,kUiDrvrSelRtId,kSetValDId,a->appId,a->usrId,a->usrId,kPanelUiCId,kIvalUiFl,0,0,NULL,tx,ty,tw,th);
651
+
652
+
653
+  _tabs->redraw();
654
+
655
+  return kOkUiRC;
656
+}
657
+
658
+cmUiRC_t  cmUiDrvrFltk::_destroyAllPanels( bool deleteWindowEleFlag )
659
+{
660
+  cmUiRC_t rc = kOkUiRC;
661
+
662
+  while( _panels != NULL )
663
+  {
664
+    cmUiRC_t rc0;
665
+    if((rc0 = _destroyCtl(_panels->appId,_panels->usrId,_panels->usrId,deleteWindowEleFlag)) != kOkUiRC )
666
+      rc = rc0;
667
+  }
668
+
669
+  return rc;
670
+}
671
+
672
+cmUiRC_t cmUiDrvrFltk::_destroyPanel(panel_t* pp, bool deleteWindowEleFlag)
673
+{
674
+  cmUiRC_t rc = kOkUiRC;
675
+
676
+  // delete the FLTK panel itself
677
+  if( deleteWindowEleFlag )
678
+  {
679
+    delete pp->grp;
680
+    deleteWindowEleFlag = false;
681
+  }
682
+
683
+  while( pp->ctls != NULL )
684
+  {
685
+    cmUiRC_t rc0;
686
+
687
+    if((rc0 = _destroyCtl(pp,pp->ctls->usrId,deleteWindowEleFlag)) != kOkUiRC )
688
+      rc = rc0;
689
+  }
690
+
691
+  cmMemFree(pp);
692
+
693
+  return rc;
694
+}
695
+
696
+cmUiRC_t cmUiDrvrFltk::_findPanel( unsigned appId, unsigned usrId, panel_t*& ppRef, panel_t*& prvPnl, bool errFl )
697
+{
698
+  ppRef  = NULL;
699
+  prvPnl = NULL;
700
+
701
+  panel_t* pp = _panels;
702
+  for(; pp!=NULL; pp=pp->link)
703
+  {
704
+    if(pp->appId==appId && pp->usrId==usrId )
705
+    {
706
+      ppRef = pp;
707
+      return kOkUiRC;
708
+    }
709
+    prvPnl = pp;
710
+  }
711
+  if( errFl )
712
+    cmErrMsg(&_err,kPanelNotFoundUiRC,"Panel not found for id=%i.",usrId);
713
+
714
+  return kPanelNotFoundUiRC;
715
+}
716
+
717
+cmUiRC_t cmUiDrvrFltk::_findCtl( panel_t* pp, unsigned usrId, ctl_t*& ctlRef, ctl_t*& prvCtlRef, bool errFl )
718
+{
719
+  ctlRef    = NULL;
720
+  prvCtlRef = NULL;
721
+  ctl_t* cp = pp->ctls;
722
+  for(; cp!=NULL; cp=cp->link)
723
+  {
724
+    if( cp->usrId == usrId )
725
+    {
726
+      ctlRef = cp;
727
+      return kOkUiRC;
728
+    }
729
+
730
+    prvCtlRef = cp;
731
+  }   
732
+  if( errFl )
733
+    cmErrMsg(&_err,kCtlNotFoundUiRC,"Control %i not found in panel %i.",usrId,pp->usrId);
734
+
735
+  return kCtlNotFoundUiRC;
736
+}
737
+
738
+void    cmUiDrvrFltk::_doCb( ctl_t* ctl, cmUiDId_t dId, unsigned flags )
739
+{
740
+  cmUiDriverArg_t* a = &ctl->cbArg;
741
+  unsigned orgFlags = a->flags;
742
+  a->flags |= flags;
743
+  a->dId    = dId;
744
+
745
+  _cbFunc(_cbArgs,&ctl->cbArg);
746
+
747
+  a->flags = orgFlags;
748
+  a->dId   = kInvalidDId;
749
+}
750
+
751
+void cmUiDrvrFltk::_s_ctl_cb(Fl_Widget* wp, void* arg )
752
+{
753
+  ctl_t*           ctl        = (ctl_t*)arg;
754
+  cmUiDrvrFltk*    p          = ctl->pnl->drvr;
755
+  cmUiDriverArg_t* a          = &ctl->cbArg;
756
+  bool             callbackFl = true;
757
+  unsigned         flags      = kValUiFl;
758
+
759
+  switch( ctl->cId )
760
+  {
761
+    case kInvalidUiCId:
762
+      assert(0);
763
+      callbackFl = false;
764
+      break;
765
+
766
+    case kPanelUiCId:
767
+      callbackFl = false;
768
+      break;
769
+
770
+    case kBtnUiCId:
771
+      break;
772
+
773
+    case kCheckUiCId:
774
+      a->ival = ctl->u.chk->value();
775
+      flags |= kIvalUiFl;
776
+      break;
777
+
778
+    case kMenuBtnUiCId:
779
+      if( ctl->u.mbt->mvalue() != NULL && ctl->u.mbt->mvalue()->label() != NULL )
780
+        ctl->u.mbt->copy_label(ctl->u.mbt->mvalue()->label());
781
+      a->ival = ctl->u.mbt->value();
782
+      flags |= kIvalUiFl;
783
+      break;
784
+
785
+    case kListUiCId:
786
+      a->ival = ctl->u.lst->value() - 1;
787
+      flags |= kIvalUiFl;
788
+      break;
789
+
790
+    case kLabelUiCId:
791
+      callbackFl = false;
792
+      break;
793
+
794
+    case kStringUiCId:
795
+      a->sval = ctl->u.str->value();
796
+      flags |= kSvalUiFl;
797
+      break;
798
+
799
+    case kConsoleUiCId:
800
+      callbackFl = false;
801
+      break;
802
+
803
+    case kSliderUiCId:
804
+      a->fval = ctl->u.sld->value();
805
+      flags |= kFvalUiFl;
806
+      break;
807
+
808
+    case kNumberUiCId:
809
+      a->fval = ctl->u.num->value();
810
+      flags |= kFvalUiFl;
811
+      break;
812
+
813
+    case kProgressUiCId:
814
+      callbackFl = false;
815
+      break;
816
+
817
+    case kMeterUiCId:
818
+      callbackFl = false;
819
+      break;
820
+
821
+    case kFilenameUiCId:
822
+      a->sval = ctl->u.fnb->filename();
823
+      flags |= kSvalUiFl;
824
+      break;
825
+
826
+    case kDirUiCId:
827
+      a->sval = ctl->u.fnb->filename();
828
+      flags |= kSvalUiFl;
829
+      break;
830
+
831
+    case kMaxUiCId:
832
+      callbackFl = false;
833
+      assert(0);
834
+      break;
835
+  }
836
+
837
+  if( callbackFl )
838
+    p->_doCb(ctl,kSetValDId,flags);
839
+  
840
+}
841
+
842
+void cmUiDrvrFltk::_s_tab_cb(Fl_Widget* wp, void* arg )
843
+{
844
+  cmUiDrvrFltk*   p   = (cmUiDrvrFltk*)arg;
845
+  Fl_Widget*      w   = p->_tabs->value();
846
+  
847
+  panel_t* pp = p->_panels;
848
+  for(; pp!=NULL; pp=pp->link)    
849
+  {
850
+    // if this is the panel being selected then send a 1 otherwise send a 0.
851
+    pp->cbArg.flags = cmSetFlag(pp->cbArg.flags, kIvalUiFl );
852
+    pp->cbArg.dId   = kSetValDId;
853
+    pp->cbArg.ival  = w->user_data() == pp->grp->user_data();
854
+
855
+    p->_cbFunc(p->_cbArgs,&pp->cbArg);
856
+
857
+    pp->cbArg.flags = cmClrFlag(pp->cbArg.flags, kIvalUiFl );
858
+    pp->cbArg.dId   = kInvalidDId;
859
+    
860
+  }
861
+
862
+}
863
+
864
+
865
+

+ 99
- 0
src/libcmpp/fltk/cmUiDrvrFltk.h View File

@@ -0,0 +1,99 @@
1
+#ifndef cmUiDrvrFltk_h
2
+#define cmUiDrvrFltk_h
3
+
4
+class Fl_Tabs;
5
+class Fl_Widget;
6
+class Fl_Button;
7
+class Fl_Check_Button;
8
+class Fl_Menu_Button;
9
+class Fl_Select_Browser;
10
+class Fl_Box;
11
+class Fl_Input;
12
+class Fl_Value_Input;
13
+class Fl_Value_Slider;
14
+class Fl_Progress;
15
+class Fl_Vert_Progress;
16
+class Fl_File_Btn; 
17
+class Fl_Text_Display;
18
+
19
+class cmUiDrvrFltk
20
+{
21
+public:
22
+
23
+  cmUiDrvrFltk(cmCtx_t* ctx, Fl_Tabs* tabs, cmUiDriverFunc_t cbFunc, void* cbArg);
24
+  virtual ~cmUiDrvrFltk();
25
+
26
+  void setBaseWindow( Fl_Tabs* tabs );
27
+  void setCallback( cmUiDriverFunc_t cbFunc, void* cbArg );
28
+
29
+  static cmUiRC_t cmUiDriverFunc( void* arg, const cmUiDriverArg_t* a );
30
+
31
+private:
32
+  struct panel_str;
33
+
34
+  typedef struct ctl_str
35
+  {
36
+    cmUiCId_t         cId;     // control type id
37
+    unsigned          usrId;   // user id
38
+    unsigned          flags;   // flags from this controls create call.
39
+    struct panel_str* pnl;     // parent panel
40
+    Fl_Widget*        wdgt;    // this controls FLTK wdgt ptr
41
+    cmUiDriverArg_t   cbArg;   // cached callback arg. recd used by this ctl
42
+    struct ctl_str*   link;    // panel.ctls list link
43
+   
44
+    union
45
+    {
46
+      Fl_Button*         btn;    
47
+      Fl_Check_Button*   chk;
48
+      Fl_Menu_Button*    mbt;
49
+      Fl_Select_Browser* lst;
50
+      Fl_Box*            lbl;
51
+      Fl_Input*          str;
52
+      Fl_Text_Display*   con;
53
+      Fl_Value_Input*    num;
54
+      Fl_Value_Slider*   sld;
55
+      Fl_Progress*       prg;
56
+      Fl_Progress*       mtr;
57
+      Fl_File_Btn*       fnb;
58
+    } u;
59
+  } ctl_t;
60
+
61
+  typedef struct panel_str
62
+  {
63
+    cmUiDrvrFltk*     drvr;   // parent driver object
64
+    Fl_Group*         grp;    // panel Widget
65
+    unsigned          appId;  // id of the app. this panel serves
66
+    unsigned          usrId;  // panels id
67
+    int               x_offs; // left control border
68
+    int               y_offs; // top control border
69
+    ctl_t*            ctls;   // this panels control list
70
+    cmUiDriverArg_t   cbArg;  // cached callback arg recd used by this ctl
71
+    struct panel_str* link;   // links used by _panels
72
+  } panel_t;
73
+
74
+  cmErr_t          _err;     //
75
+  Fl_Tabs*         _tabs;    // Fl_Tabs Widget containing the panels
76
+  cmUiDriverFunc_t _cbFunc;  // application event callback function
77
+  void*            _cbArgs;  // 
78
+  panel_t*         _panels;  // panel list
79
+  ctl_t            _dummy;   // 
80
+    
81
+  void        _insertNewCtl( panel_t* pp, ctl_t* ctl, Fl_Widget* wp, unsigned flags );
82
+  bool        _hasNoAlignFlags( unsigned flags ) const;
83
+  cmUiRC_t    _createCtl(   const cmUiDriverArg_t* a );
84
+  cmUiRC_t    _destroyCtl(  unsigned appId, unsigned panelId, unsigned usrId, bool deleteWindowEleFlag );
85
+  cmUiRC_t    _destroyCtl(  panel_t* pp, unsigned usrId, bool deleteWindowEleFlag );
86
+  cmUiRC_t    _createPanel( const cmUiDriverArg_t* a );
87
+  cmUiRC_t    _setValueCtl( const cmUiDriverArg_t* a );
88
+  cmUiRC_t    _enableCtl( const cmUiDriverArg_t* a );
89
+  cmUiRC_t    _destroyAllPanels( bool deleteWindowEleFl );
90
+  cmUiRC_t    _destroyPanel(panel_t* pp, bool deleteWindowEleFl );
91
+  cmUiRC_t    _findPanel( unsigned appId, unsigned usrId, panel_t*& ppRef, panel_t*& prvPnlRef, bool errFl=true );
92
+  cmUiRC_t    _findCtl( panel_t* pp, unsigned usrId, ctl_t*& ctlRef, ctl_t*& prvCtlRef, bool errFl=true );
93
+  void        _doCb( ctl_t* ctl, cmUiDId_t dId, unsigned flags );
94
+
95
+  static void _s_ctl_cb(Fl_Widget* wp, void* data );
96
+  static void _s_tab_cb(Fl_Widget* wp, void* data );
97
+};
98
+
99
+#endif

+ 11
- 0
src/tlCtl/Makefile.am View File

@@ -0,0 +1,11 @@
1
+
2
+
3
+tlCtlSRC  = src/tlCtl/cmdIf.h        src/tlCtl/cmdIf.cpp
4
+tlCtlSRC += src/tlCtl/gvHashFunc.h   src/tlCtl/gvHashFunc.cpp
5
+tlCtlSRC += src/tlCtl/cmGrTlFltk.h   src/tlCtl/cmGrTlFltk.cpp
6
+tlCtlSRC += src/tlCtl/cmGrScFltk.h   src/tlCtl/cmGrScFltk.cpp
7
+tlCtlSRC += src/tlCtl/cmGrTksbFltk.h src/tlCtl/cmGrTksbFltk.cpp
8
+tlCtlSRC += src/tlCtl/cmGrTksrFltk.h src/tlCtl/cmGrTksrFltk.cpp
9
+tlCtlSRC += src/tlCtl/cmGr2dFltk.h   src/tlCtl/cmGr2dFltk.cpp
10
+
11
+tlCtlSRC += src/tlCtl/tlCtl.h        src/tlCtl/tlCtl.cpp

+ 148
- 0
src/tlCtl/cmGr2dFltk.cpp View File

@@ -0,0 +1,148 @@
1
+#include <FL/Fl.H>
2
+#include <Fl/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+#include <Fl/Fl_Menu_Bar.H>
7
+
8
+#include <vector>
9
+
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmGlobal.h"
13
+#include "cmFloatTypes.h"
14
+#include "cmRpt.h"
15
+#include "cmErr.h"
16
+#include "cmCtx.h"
17
+#include "cmMem.h"
18
+#include "cmMallocDebug.h"
19
+#include "cmLinkedHeap.h"
20
+#include "cmText.h"
21
+
22
+#include "cmGr.h"
23
+#include "cmGrDevCtx.h"
24
+#include "cmGrPlot.h"
25
+#include "cmGrPage.h"
26
+#include "cmGrFltk.h"
27
+#include "cmGr2dFltk.h"
28
+
29
+
30
+cmGr2dFltk::cmGr2dFltk(cmCtx_t* ctx, Fl_Menu_Bar* menuBar, int x, int y, int w, int h)
31
+  : cmGrPlotFltk(ctx,x,y,w,h),
32
+    _x(0),_y(0),_radius(0),_angle(0),
33
+    _objId(0)
34
+{
35
+  cmErrSetup(&_err,&ctx->rpt,"cmGr2dFltk");
36
+
37
+  if( cmGrPageIsValid(pageHandle()) == false )
38
+    return;
39
+
40
+  initViews(1,1);
41
+
42
+  unsigned   vwIdx = 0;
43
+  cmGrPgH_t  pgH   = pageHandle();
44
+  cmGrVwH_t  vwH   = cmGrPageViewHandle( pgH, vwIdx);
45
+  cmGrH_t    cvH   = cmGrViewGrHandle( vwH );
46
+  cmGrVExt_t limExt;
47
+
48
+  cmGrVExtSetD(&limExt,-kWidth,-kHeight,kWidth, kHeight);
49
+
50
+  cmGrObjSetWorldExt( cvH, cmGrRootObjH(cvH), &limExt );
51
+  cmGrObjSetWorldLimitExt(cvH, cmGrRootObjH(cvH), &limExt, kLeftGrFl | kRightGrFl | kTopGrFl | kBottomGrFl );
52
+
53
+  _createObj();
54
+
55
+  cmGrSetViewExtentsE( cvH,  &limExt );
56
+
57
+}
58
+
59
+cmGr2dFltk::~cmGr2dFltk()
60
+{
61
+}
62
+
63
+
64
+bool cmGr2dFltk::on_plot_object( cmGrPlotCbArg_t* arg )
65
+{
66
+  if(  arg->selId==kEventCbSelGrPlId && cmIsFlag(arg->eventFlags,kMsDragGrFl ) )
67
+  {
68
+    cmGrVExt_t vext;
69
+    cmGrPlotObjVExt(arg->objH,&vext);
70
+    //cmGrVExtPrint("",&vext);
71
+    _x = cmGrVExtMinX(&vext);
72
+    _y = cmGrVExtMinY(&vext);
73
+    _radius = sqrtf(_x*_x + _y*_y)/kWidth;
74
+    _angle  = -( atan2f(_y,_x) - M_PI/2.0);
75
+
76
+    if( _angle < 0 )
77
+      _angle += 2.0 * M_PI;
78
+
79
+    _angle = 360.0f * _angle / (2.0*M_PI);
80
+
81
+    setStatusText(cmTsPrintfS("r:%f angle:%f",_radius,_angle));
82
+
83
+    callback()(this,user_data());
84
+
85
+  }
86
+
87
+  return true;
88
+}
89
+
90
+
91
+double cmGr2dFltk::x() const
92
+{ return _x; }
93
+
94
+double cmGr2dFltk::y() const
95
+{ return _y; }
96
+
97
+double cmGr2dFltk::radius() const
98
+{ return _radius; }
99
+
100
+double cmGr2dFltk::angle() const
101
+{ return _angle; }
102
+
103
+void cmGr2dFltk::_createObj()
104
+{
105
+  cmGrPlH_t         plH         = plotHandle();
106
+  cmGrPgH_t         pgH         = pageHandle();
107
+  unsigned          vwIdx       = 0;
108
+  cmGrVwH_t         vwH         = cmGrPageViewHandle( pgH, vwIdx );
109
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
110
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
111
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
112
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
113
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
114
+  cmGrPlObjTypeId_t objTypeId   = kRectGrPlId;
115
+  cmReal_t          x           = 0;
116
+  cmReal_t          y           = 0;
117
+  cmReal_t          w           = 0;
118
+  cmReal_t          h           = 0;
119
+  unsigned          flags       = 0; //kNoDragGrPlFl;
120
+  cmGrVExt_t*       wext        = NULL;
121
+
122
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags | kNoDragGrPlFl, x, y, w, h, NULL, wext ) != kOkGrPlRC )
123
+  {
124
+    cmErrMsg(&_err,kCreateObjRC,"Plot origin object create failed.");
125
+  }
126
+  else
127
+  {
128
+    cmGrPlotObjSetPhysExt(objH, -2, -2, 2, 2 );
129
+    cmGrPlotObjSetFontSize(objH,8);
130
+  }
131
+    
132
+  objH = cmGrPlObjNullHandle;
133
+
134
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, NULL, wext ) != kOkGrPlRC )
135
+  {
136
+    cmErrMsg(&_err,kCreateObjRC,"Plot object create failed.");
137
+  }
138
+  else
139
+  {
140
+    //unsigned f  = 0 ? (kNorthJsGrFl | kTopJsGrFl) : (kSouthJsGrFl | kBottomJsGrFl);
141
+    //cmGrPlotObjSetLabelAttr( objH,  f | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, kBlackGrId );
142
+    cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kGreenGrId );
143
+    cmGrPlotObjSetPhysExt(objH, -4, -4, 4, 4 );
144
+    cmGrPlotObjSetFontSize(objH,8);
145
+  }
146
+
147
+}
148
+

+ 44
- 0
src/tlCtl/cmGr2dFltk.h View File

@@ -0,0 +1,44 @@
1
+#ifndef cmGr2dFltk_h
2
+#define cmGr2dFltk_h
3
+
4
+class Fl_Menu_Bar;
5
+
6
+class cmGr2dFltk : public cmGrPlotFltk
7
+{
8
+public:
9
+  cmGr2dFltk(cmCtx_t* ctx, Fl_Menu_Bar* menuBar, int x, int y, int w, int h);
10
+
11
+  virtual ~cmGr2dFltk();
12
+
13
+  virtual bool on_plot_object( cmGrPlotCbArg_t* arg );
14
+
15
+  double x() const;
16
+  double y() const;
17
+  double radius() const;
18
+  double angle() const;
19
+
20
+private:
21
+  enum
22
+  {
23
+    kWidth = 100,
24
+    kHeight = 100
25
+  };
26
+
27
+  enum
28
+  {
29
+    kOkRC = 0,
30
+    kCreateObjRC
31
+  };
32
+
33
+  cmErr_t _err;
34
+  double _x;
35
+  double _y;
36
+  double _radius;
37
+  double _angle;
38
+  unsigned _objId;
39
+
40
+  void _createObj();
41
+  
42
+};
43
+
44
+#endif

+ 565
- 0
src/tlCtl/cmGrScFltk.cpp View File

@@ -0,0 +1,565 @@
1
+#include <FL/Fl.H>
2
+#include <Fl/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+#include <Fl/Fl_Menu_Bar.H>
7
+
8
+#include <vector>
9
+
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmGlobal.h"
13
+#include "cmFloatTypes.h"
14
+#include "cmRpt.h"
15
+#include "cmErr.h"
16
+#include "cmCtx.h"
17
+#include "cmMem.h"
18
+#include "cmMallocDebug.h"
19
+#include "cmLinkedHeap.h"
20
+#include "cmText.h"
21
+#include "cmThread.h"
22
+#include "cmPrefs.h"
23
+#include "cmSymTbl.h"
24
+#include "cmTime.h"
25
+#include "cmMidi.h"
26
+#include "cmMidiFile.h"
27
+#include "cmAudioFile.h"
28
+#include "cmAudioFileMgr.h"
29
+#include "cmTimeLine.h"
30
+#include "cmScore.h"
31
+
32
+#include "cmGr.h"
33
+#include "cmGrDevCtx.h"
34
+#include "cmGrPlot.h"
35
+#include "cmGrPage.h"
36
+#include "cmGrFltk.h"
37
+#include "gvHashFunc.h"
38
+#include "cmGrScFltk.h"
39
+#include "cmGrPlotAudio.h"
40
+#include "cmdIf.h"
41
+
42
+cmGrScFltk::cmGrScFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menu, int x, int y, int w, int h)
43
+  : cmGrPlotFltk(ctx,x,y,w,h),
44
+    _srate(0),_cmdIf(cp),_menuBar(menu),
45
+    _samplesMetricId(cmInvalidId),_secondsMetricId(cmInvalidId),
46
+    _objSecs(0),_objId(0),
47
+    _togFl(true),
48
+    _lastBarPlotObjH(cmGrPlObjNullHandle)
49
+{
50
+  cmErrSetup(&_err,&ctx->rpt,"cmGrScFltk");
51
+
52
+  _createMenu();
53
+
54
+  if( cmGrPageIsValid(pageHandle()) == false )
55
+    return;
56
+
57
+  initViews(1,1);
58
+
59
+  unsigned   vwIdx = 0;
60
+  cmGrPgH_t  pgH   = pageHandle();
61
+  cmGrVwH_t  vwH   = cmGrPageViewHandle( pgH, vwIdx);
62
+  cmGrH_t    cvH   = cmGrViewGrHandle( vwH );
63
+  cmGrAxH_t  axH   = cmGrAxNullHandle;
64
+  cmGrVExt_t limExt;
65
+
66
+  _samplesMetricId = cmGrPageLabelFuncRegister( pgH, gvRoundHashValueFunc,    this, "Round" );              
67
+  _secondsMetricId = cmGrPageLabelFuncRegister( pgH, gvMinSecMsHashValueFunc, this, "Min:Sec:Ms" );              
68
+  unsigned pitchLabelFuncId  = cmGrPageLabelFuncRegister( pgH, gvMidiSciPitchValueFunc, this, "Pitch" );
69
+
70
+  cmGrVExtSetD(&limExt,0,0,0,127);
71
+  cmGrObjSetWorldExt( cvH, cmGrRootObjH(cvH), &limExt );
72
+
73
+  cmGrObjSetWorldLimitExt(cvH, cmGrRootObjH(cvH), &limExt, kTopGrFl | kBottomGrFl );
74
+
75
+  axH = cmGrViewAxisHandle(vwH, kTopGrIdx);
76
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashMarkGrFl | kHashLabelGrFl ));
77
+
78
+  axH = cmGrViewAxisHandle(vwH, kLeftGrIdx );
79
+  cmGrAxisSetLabelFunc( axH, pitchLabelFuncId );
80
+  cmGrViewSetLabelFunc(  vwH, kLeftGrIdx, pitchLabelFuncId );
81
+  
82
+  axH = cmGrViewAxisHandle(vwH, kRightGrIdx);
83
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashLabelGrFl ));
84
+
85
+  cmGrViewSetCfg( vwH, cmSetFlag(cmGrViewCfg(vwH),kSelectHorzGrFl)  );
86
+
87
+}
88
+
89
+cmGrScFltk::~cmGrScFltk()
90
+{
91
+}
92
+
93
+cmScMsgTypeId_t cmGrScFltk::recvScoreMsg( const void* msg, unsigned msgByteCnt )
94
+{
95
+  cmScMsg_t m;
96
+
97
+  cmScoreDecode(msg,msgByteCnt,&m);
98
+
99
+  switch( m.typeId )
100
+  {
101
+    case kBeginMsgScId:
102
+      {
103
+        _objId   = 0;
104
+        _objSecs = 0;
105
+        // remove all objects from all views
106
+        //cmGrPageClear(pageHandle());
107
+        //_srate = m.srate;
108
+        //_updateSeqMenu(m.seqCnt,m.seqId);
109
+      }
110
+      break;
111
+
112
+    case kEndMsgScId:
113
+      //size(w(),h()+1);
114
+      break;
115
+
116
+    case kEventMsgScId:
117
+      _insertEvent(&m.u.evt);
118
+      break;
119
+
120
+    case kSectionMsgScId:
121
+      _insertSection(&m.u.sect);
122
+      break;
123
+      
124
+    case kVarMsgScId:
125
+      break;
126
+
127
+    default:
128
+      { assert(0); }
129
+  }
130
+
131
+  return m.typeId;
132
+}
133
+
134
+void cmGrScFltk::setSampleRate( double srate )
135
+{ _srate = srate; }
136
+
137
+double cmGrScFltk::sampleRate() const 
138
+{ return _srate; }
139
+
140
+bool cmGrScFltk::on_plot_object(   cmGrPlotCbArg_t* arg )
141
+{
142
+  if(  arg->selId==kStateChangeGrPlId && cmIsFlag(arg->deltaFlags,kSelectGrPlFl) )
143
+  {
144
+    scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(arg->objH);
145
+
146
+    if( sop!=NULL && sop->id==kEventMsgScId && sop->u.ep != NULL /* && sep->type == kBarEvtScId */ )
147
+    {
148
+      _lastBarPlotObjH = arg->objH;
149
+      
150
+      unsigned scoreIdx = scoreSelectedEleIndex();
151
+
152
+      // callback to: kcApp::_ctl_cb(ctl_t* cp)
153
+      callback()(this,user_data());
154
+
155
+      _cmdIf->onScoreBarSelected(scoreIdx);
156
+    
157
+      setStatusText(cmTsPrintfS("Score Index:%i",scoreIdx));
158
+    }
159
+  }
160
+  return true;
161
+}
162
+
163
+void cmGrScFltk::selectBar( unsigned barNumb )
164
+{
165
+  cmGrPlH_t plH = plotHandle();
166
+  unsigned  n   = cmGrPlotObjectCount(plH);
167
+  unsigned  i;
168
+  for(i=0; i<n; ++i)
169
+  {
170
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
171
+
172
+    if( cmGrPlotObjIsValid(poH) )
173
+    {
174
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
175
+
176
+      if( sop->id==kEventMsgScId && sop->u.ep!=NULL && sop->u.ep->type==kBarEvtScId && sop->u.ep->barNumb==barNumb )
177
+      {
178
+        unsigned flags = cmGrPlotObjStateFlags(poH);
179
+        
180
+        cmGrPlotObjSetStateFlags(poH,cmSetFlag(flags,kFocusGrPlFl | kSelectGrPlFl));
181
+        redraw();
182
+
183
+        _lastBarPlotObjH = poH;
184
+        
185
+        _cmdIf->onScoreBarSelected(sop->u.ep->locIdx);
186
+    
187
+        setStatusText(cmTsPrintfS("Score Index:%i",sop->u.ep->locIdx));
188
+
189
+        break;
190
+      }
191
+    }
192
+  }
193
+  
194
+}
195
+
196
+unsigned cmGrScFltk::scoreSelectedEleIndex() const
197
+{ 
198
+
199
+  if( cmGrPlotObjIsValid(_lastBarPlotObjH) )
200
+  {
201
+    scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(_lastBarPlotObjH);
202
+
203
+    if( sop!=NULL && sop->id==kEventMsgScId && sop->u.ep != NULL /* && sop->u.ep->type == kBarEvtScId */ )
204
+      return sop->u.ep->locIdx;
205
+  }
206
+  return cmInvalidIdx;
207
+}
208
+
209
+void cmGrScFltk::setScoreLocation( unsigned locIdx, unsigned vel, unsigned smpIdx )
210
+{
211
+  
212
+}
213
+
214
+void cmGrScFltk::_insertSection( const cmScoreSection_t* m )
215
+{
216
+  // The argument is a serialzed copy of a cmScoreSection_t record.
217
+  // Convert it to a pointer to an actual object in the local score mgr.
218
+  if( cmGrPageIsValid(pageHandle()) == false )
219
+    return;
220
+
221
+  m = _cmdIf->scoreSectionIdToPtr(m->index);
222
+  assert(m!=NULL);
223
+
224
+  const cmScoreEvt_t* ep = _cmdIf->scoreEventIdToPtr(m->begEvtIndex);
225
+  assert( ep != NULL );
226
+
227
+
228
+  cmGrPlH_t         plH         = plotHandle();
229
+  cmGrPgH_t         pgH         = pageHandle();
230
+  unsigned          vwIdx       = 0;
231
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
232
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
233
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
234
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
235
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
236
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
237
+  cmGrPlObjTypeId_t objTypeId   = kLineGrPlId;
238
+  cmReal_t          x           = ep->secs;
239
+  cmReal_t          y           = 120;
240
+  cmReal_t          w           = 0;
241
+  cmReal_t          h           = 7;
242
+  const cmChar_t*   label       = m->label;
243
+  unsigned          flags       = kNoDragGrPlFl;
244
+  cmGrVExt_t        wext;
245
+  scObj_t           scObj(m);
246
+  
247
+  cmGrVExtSetNull(&wext);
248
+
249
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
250
+  {
251
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on a score section.", cmStringNullGuard(label));
252
+    return;
253
+  }
254
+
255
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
256
+
257
+  unsigned f  = 0 ? (kNorthJsGrFl | kTopJsGrFl) : (kSouthJsGrFl | kBottomJsGrFl);
258
+  cmGrPlotObjSetLabelAttr( objH,  f | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, kBlackGrId );
259
+  cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kGreenGrId );
260
+  //cmGrPlotObjSetPhysExt(objH, 1, 0, 1, 0 );
261
+  cmGrPlotObjSetFontSize(objH,8);
262
+  
263
+  
264
+}
265
+
266
+void cmGrScFltk::_insertEvent( const cmScoreEvt_t* m )
267
+{
268
+  // The argument is a serialzed copy of a cmScoreEvt record.
269
+  // Convert it to a pointer to an actual object in the local score mgr.
270
+  if( cmGrPageIsValid(pageHandle()) == false )
271
+    return;
272
+
273
+  m = _cmdIf->scoreEventIdToPtr(m->index);
274
+  assert(m!=NULL);
275
+    
276
+  cmGrPlH_t         plH         = plotHandle();
277
+  cmGrPgH_t         pgH         = pageHandle();
278
+  unsigned          vwIdx       = 0;
279
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
280
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
281
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
282
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
283
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
284
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
285
+  cmGrPlObjTypeId_t objTypeId   = kVLineGrPlId;
286
+  cmReal_t          x           = m->secs;
287
+  cmReal_t          y           = 0;
288
+  cmReal_t          w           = 0;
289
+  cmReal_t          h           = 127;
290
+  const cmChar_t*   label       = NULL;
291
+  unsigned          flags       = kNoDragGrPlFl;
292
+  int               bufN        = 7;
293
+  cmChar_t          buf[bufN+1];
294
+  cmGrVExt_t        wext;
295
+  scObj_t           scObj(m);
296
+
297
+  cmGrVExtSetNull(&wext);
298
+
299
+  switch( m->type )
300
+  {
301
+    case kNonEvtScId:
302
+      objTypeId = kRectGrPlId;
303
+      y         = m->pitch;
304
+      h         = 1;
305
+      w         = m->durSecs;
306
+      label     = cmMidiToSciPitch(m->pitch,NULL,0);
307
+      break;
308
+
309
+    case kBarEvtScId:
310
+      {
311
+        buf[bufN] = 0;
312
+        snprintf(buf,bufN,"%i",m->barNumb);
313
+        objTypeId = kVLineGrPlId;
314
+        label     = buf;
315
+      }
316
+      break;
317
+
318
+    case kPedalEvtScId:
319
+      if( cmIsFlag(m->flags, kPedalDnScFl ) == false )
320
+        return;
321
+
322
+      objTypeId = kRectGrPlId;
323
+      y         = m->pitch;   // pedal type (damper=64, sostenuto=66) is held in pitch
324
+      h         = 1;
325
+      w         = m->durSecs;
326
+      flags    += kNoFillGrPlFl;
327
+      break;
328
+
329
+    default:
330
+      return;
331
+  }    
332
+
333
+
334
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
335
+  {
336
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on a score event.", cmStringNullGuard(label));
337
+    return;
338
+  }
339
+
340
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
341
+
342
+
343
+  switch( m->type )
344
+  {
345
+    case kBarEvtScId:
346
+      {
347
+        unsigned f  = _togFl ? (kNorthJsGrFl | kTopJsGrFl) : (kSouthJsGrFl | kBottomJsGrFl);
348
+        cmGrPlotObjSetLabelAttr( objH,  f | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, kBlueGrId );
349
+        cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kYellowGrId );
350
+        cmGrPlotObjSetPhysExt(objH, 1, 0, 1, 0 );
351
+        _togFl = !_togFl;
352
+      }
353
+      break;
354
+
355
+    case kNonEvtScId:
356
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, cmGrPlotObjFillColor(objH,kEnablePlGrId) );
357
+      cmGrPlotObjSetFontSize(objH,8);
358
+      break;
359
+
360
+    case kPedalEvtScId:
361
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, y==64 ? kDarkGreenGrId : kLightGreenGrId   );
362
+      break;
363
+
364
+    default:
365
+      break;
366
+  }
367
+
368
+  if( cmIsFlag(m->flags,kInvalidScFl) )
369
+  {
370
+    cmGrPlotObjSetFillColor(objH, kEnablePlGrId, kRedGrId );
371
+  }
372
+
373
+}
374
+
375
+void cmGrScFltk::_createMenu( )
376
+{
377
+  int idx = _menuBar->add("Score",0,NULL,0,FL_SUBMENU);
378
+  const char* titleArray[] = { "Pitch", "Attributes", "Dynamics", "Location", "Fraction", "Section Even", "Section Dyn", "Section Tempo" };
379
+  bool        onFl[]       = { true,     false,        false,     false,       false,     false,          false,         false };
380
+  int i;
381
+  for(i=0; i<kMenuItemCnt; ++i)
382
+  {
383
+    _menuArray[i].id = i;
384
+    _menuArray[i].p  = this;
385
+    _menuBar->insert(idx+1+i,titleArray[i],0,_s_menuCallback, _menuArray + i, FL_MENU_TOGGLE );  
386
+
387
+    if( onFl[i] )
388
+    {
389
+      Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + idx + i + 1;
390
+      mip->set();
391
+    }
392
+  }
393
+}
394
+
395
+bool cmGrScFltk::_isMenuChecked( int id )
396
+{
397
+  unsigned i;
398
+  // locate the menu item assoc'd with id
399
+  for(i=0; i<kMenuItemCnt; ++i)
400
+    if( _menuArray[i].id == id )
401
+      break;
402
+
403
+  assert( i < kMenuItemCnt );
404
+
405
+  int menuIdx;
406
+  if(( menuIdx = _menuBar->find_index("Score")) == -1 )
407
+    return false;
408
+  
409
+  // The menu items and _menuArray[] were initialized in the same order
410
+  // therefore the offset from the base of both should be the same.
411
+  Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + menuIdx + i + 1;
412
+
413
+  assert( (item_t*)mip->user_data() == _menuArray + i );
414
+
415
+  return mip->value() != 0;
416
+}
417
+
418
+void cmGrScFltk::_setEventLabels()
419
+{
420
+  enum { kPitchFl=0x01, kAttrFl=0x02, kDynFl=0x04, kLocFl=0x08, kFracFl=0x10 };
421
+ 
422
+  cmGrPlH_t plH = plotHandle();
423
+  unsigned flags = 0;
424
+  flags |= _isMenuChecked(kPitchMId)  ? kPitchFl : 0;
425
+  flags |= _isMenuChecked(kAttrMId)   ? kAttrFl  : 0;
426
+  flags |= _isMenuChecked(kDynMId)    ? kDynFl   : 0;
427
+  flags |= _isMenuChecked(kLocIdxMId) ? kLocFl   : 0;
428
+  flags |= _isMenuChecked(kFracMId)   ? kFracFl  : 0;
429
+ 
430
+  unsigned n = cmGrPlotObjectCount(plH);
431
+  unsigned i;
432
+  for(i=0; i<n; ++i)
433
+  {
434
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
435
+
436
+    if( cmGrPlotObjIsValid(poH) )
437
+    {
438
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
439
+      
440
+      if( sop!=NULL && sop->id==kEventMsgScId && sop->u.ep!=NULL && sop->u.ep->type==kNonEvtScId )
441
+      {
442
+        const cmScoreEvt_t* ep   = sop->u.ep;
443
+        int           bufN = 255;
444
+        cmChar_t buf[ bufN+1 ];
445
+
446
+        buf[bufN] = 0;
447
+        buf[0]    = 0;
448
+
449
+        if( cmIsFlag(flags,kPitchFl) )
450
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",cmMidiToSciPitch(ep->pitch,NULL,0));
451
+
452
+        if( cmIsFlag(flags,kAttrFl) )
453
+        {
454
+          cmChar_t s[4]; 
455
+          int      j=0;
456
+          if( cmIsFlag(ep->flags,kEvenScFl) )
457
+            s[j++] = 'e';
458
+          if( cmIsFlag(ep->flags,kDynScFl) )
459
+            s[j++] = 'd';
460
+          if( cmIsFlag(ep->flags,kTempoScFl) )
461
+            s[j++] = 't';
462
+          s[j] = 0;
463
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",s);
464
+        }
465
+      
466
+
467
+        if( cmIsFlag(flags,kDynFl) && cmIsFlag(ep->flags,kDynScFl) )
468
+        {
469
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"d:%i",ep->dynVal);
470
+
471
+          if( ep->perfDynLvl != 0 )
472
+            snprintf(buf+strlen(buf),bufN-strlen(buf),"|%i ",ep->perfDynLvl);
473
+          else
474
+            snprintf(buf+strlen(buf),bufN-strlen(buf)," ");
475
+        }
476
+
477
+        if( cmIsFlag(flags,kLocFl) )
478
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"loc:%i ",ep->locIdx);
479
+
480
+        if( cmIsFlag(flags,kFracFl) && ep->frac != 0)
481
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%5.3f ",ep->frac);
482
+
483
+        cmGrPlotObjSetLabel(poH, buf );
484
+      }
485
+    }
486
+  }
487
+}
488
+
489
+void cmGrScFltk::_setSectionLabels()
490
+{
491
+ enum { kEvenFl=0x01, kDynFl=0x02, kTempoFl=0x04 };
492
+ 
493
+  cmGrPlH_t plH = plotHandle();
494
+  unsigned flags = 0;
495
+  flags |= _isMenuChecked(kSectEvenMId)  ? kEvenFl  : 0;
496
+  flags |= _isMenuChecked(kSectDynMId)   ? kDynFl   : 0;
497
+  flags |= _isMenuChecked(kSectTempoMId) ? kTempoFl : 0;
498
+ 
499
+  unsigned n = cmGrPlotObjectCount(plH);
500
+  unsigned i;
501
+  for(i=0; i<n; ++i)
502
+  {
503
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
504
+
505
+    if( cmGrPlotObjIsValid(poH) )
506
+    {
507
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
508
+      
509
+      if( sop!=NULL && sop->id==kSectionMsgScId && sop->u.sp!=NULL )
510
+      {
511
+        const cmScoreSection_t* sp   = sop->u.sp;
512
+        int           bufN = 255;
513
+        cmChar_t buf[ bufN+1 ];
514
+
515
+        buf[bufN] = 0;
516
+        buf[0]    = 0;
517
+
518
+        snprintf(buf,bufN,"%s ",sp->label);
519
+
520
+        if( cmIsFlag(flags,kEvenFl) && sp->vars[kEvenVarScId] != DBL_MAX)
521
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"e:%f ",sp->vars[kEvenVarScId]);
522
+
523
+        if( cmIsFlag(flags,kDynFl)  && sp->vars[kDynVarScId] != DBL_MAX)
524
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"d:%f ",sp->vars[kDynVarScId]);
525
+
526
+        if( cmIsFlag(flags,kTempoFl)  && sp->vars[kTempoVarScId] != DBL_MAX)
527
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"t:%f ",sp->vars[kTempoVarScId]);
528
+               
529
+        cmGrPlotObjSetLabel(poH, buf );
530
+      }
531
+    }
532
+  }
533
+   
534
+}
535
+
536
+void cmGrScFltk::_s_menuCallback(Fl_Widget* w, void* arg )
537
+{
538
+  item_t*          ip = (item_t*)arg;
539
+  cmGrScFltk*      p  = ip->p;
540
+  unsigned long    id = ip->id;
541
+
542
+  switch( id )
543
+  {
544
+    case kPitchMId:
545
+    case kAttrMId:
546
+    case kDynMId:
547
+    case kLocIdxMId:
548
+    case kFracMId:
549
+      {
550
+        p->_setEventLabels();
551
+        p->redraw();
552
+      }
553
+      break;
554
+
555
+    case kSectEvenMId:
556
+    case kSectDynMId:
557
+    case kSectTempoMId:
558
+      {
559
+        p->_setSectionLabels();
560
+        p->redraw();
561
+      }
562
+      break;
563
+  }
564
+}
565
+

+ 89
- 0
src/tlCtl/cmGrScFltk.h View File

@@ -0,0 +1,89 @@
1
+#ifndef cmGrScFltk_h
2
+#define cmGrScFltk_h
3
+
4
+class Fl_Menu_Bar;
5
+class cmdIf;
6
+
7
+class cmGrScFltk : public cmGrPlotFltk, public gvHashFuncArg
8
+{
9
+ public:
10
+  cmGrScFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menuBar, int x, int y, int w, int h);
11
+  virtual ~cmGrScFltk();
12
+
13
+  virtual cmScMsgTypeId_t recvScoreMsg( const void* msg, unsigned msgByteCnt );
14
+
15
+  void setSampleRate( double srate );
16
+  virtual double sampleRate() const;
17
+
18
+  virtual bool on_plot_object( cmGrPlotCbArg_t* arg );
19
+
20
+  virtual void selectBar( unsigned barNumb );
21
+  
22
+  virtual unsigned scoreSelectedEleIndex() const;
23
+
24
+  virtual void setScoreLocation( unsigned locIdx, unsigned vel, unsigned smpIdx );
25
+
26
+ private:
27
+  enum
28
+  {
29
+    kOkRC,
30
+    kInsertObjFailRC
31
+  };
32
+
33
+  enum
34
+  {
35
+    kPitchMId,
36
+    kAttrMId,
37
+    kDynMId,
38
+    kLocIdxMId,
39
+    kFracMId,
40
+    kSectEvenMId,
41
+    kSectDynMId,
42
+    kSectTempoMId,
43
+    kMenuItemCnt
44
+  };
45
+
46
+  typedef struct
47
+  {
48
+    cmGrScFltk* p;
49
+    int         id;
50
+  } item_t;
51
+
52
+  typedef struct scObj_str
53
+  {
54
+    cmScMsgTypeId_t id; // kEventMsgScId | kSectionMsgScId 
55
+    union
56
+    {
57
+      const cmScoreEvt_t*     ep;
58
+      const cmScoreSection_t* sp;
59
+    } u;
60
+
61
+    scObj_str( const cmScoreEvt_t* e)     : id(kEventMsgScId)   {u.ep=e;}
62
+    scObj_str( const cmScoreSection_t* s) : id(kSectionMsgScId) {u.sp=s;}
63
+  } scObj_t;
64
+
65
+  double       _srate;
66
+  cmErr_t      _err;
67
+  cmdIf*       _cmdIf;
68
+  Fl_Menu_Bar* _menuBar;
69
+  unsigned     _samplesMetricId;
70
+  unsigned     _secondsMetricId;
71
+  double       _objSecs;
72
+  unsigned     _objId;
73
+  bool         _togFl; 
74
+  cmGrPlObjH_t _lastBarPlotObjH;
75
+  item_t       _menuArray[ kMenuItemCnt ];
76
+
77
+  void _insertSection( const cmScoreSection_t* s );
78
+  void _insertEvent( const cmScoreEvt_t* m );
79
+  void _createMenu();
80
+  bool _isMenuChecked( int id );
81
+  void _setEventLabels();
82
+  void _setSectionLabels();
83
+
84
+  static void _s_menuCallback(Fl_Widget* w, void* arg);
85
+  
86
+};
87
+
88
+
89
+#endif

+ 695
- 0
src/tlCtl/cmGrTksbFltk.cpp View File

@@ -0,0 +1,695 @@
1
+#include <FL/Fl.H>
2
+#include <Fl/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+#include <Fl/Fl_Menu_Bar.H>
7
+
8
+#include <vector>
9
+
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmGlobal.h"
13
+#include "cmFloatTypes.h"
14
+#include "cmRpt.h"
15
+#include "cmErr.h"
16
+#include "cmCtx.h"
17
+#include "cmMem.h"
18
+#include "cmMallocDebug.h"
19
+#include "cmLinkedHeap.h"
20
+#include "cmText.h"
21
+#include "cmThread.h"
22
+#include "cmPrefs.h"
23
+#include "cmSymTbl.h"
24
+#include "cmTime.h"
25
+#include "cmMidi.h"
26
+#include "cmMidiFile.h"
27
+#include "cmAudioFile.h"
28
+#include "cmAudioFileMgr.h"
29
+#include "cmTimeLine.h"
30
+#include "cmScore.h"
31
+#include "cmTakeSeqBldr.h"
32
+
33
+#include "cmGr.h"
34
+#include "cmGrDevCtx.h"
35
+#include "cmGrPlot.h"
36
+#include "cmGrPage.h"
37
+#include "cmGrFltk.h"
38
+#include "gvHashFunc.h"
39
+#include "cmGrTksbFltk.h"
40
+#include "cmGrPlotAudio.h"
41
+#include "cmdIf.h"
42
+
43
+cmGrTksbFltk::cmGrTksbFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menu, int x, int y, int w, int h)
44
+  : cmGrPlotFltk(ctx,x,y,w,h),
45
+    //_cmdIf(cp),
46
+    _tksbH(cmTakeSeqBldrNullHandle),
47
+    _menuBar(menu),
48
+    _samplesMetricId(cmInvalidId),_secondsMetricId(cmInvalidId),
49
+    //_objSecs(0),
50
+    _objId(0),
51
+    //_togFl(true),
52
+  _lastBarPlotObjH(cmGrPlObjNullHandle),
53
+  _nextTakeY(5),
54
+  _curCbTId(kInvalidTId)
55
+{
56
+  cmErrSetup(&_err,&ctx->rpt,"cmGrTksbFltk");
57
+
58
+  _createMenu();
59
+
60
+  if( cmGrPageIsValid(pageHandle()) == false )
61
+    return;
62
+
63
+  initViews(1,1);
64
+
65
+  unsigned   vwIdx = 0;
66
+  cmGrPgH_t  pgH   = pageHandle();
67
+  cmGrVwH_t  vwH   = cmGrPageViewHandle( pgH, vwIdx);
68
+  cmGrH_t    cvH   = cmGrViewGrHandle( vwH );
69
+  cmGrAxH_t  axH   = cmGrAxNullHandle;
70
+  cmGrVExt_t limExt;
71
+
72
+  _samplesMetricId = cmGrPageLabelFuncRegister( pgH, gvRoundHashValueFunc,    this, "Round" );              
73
+  _secondsMetricId = cmGrPageLabelFuncRegister( pgH, gvMinSecMsHashValueFunc, this, "Min:Sec:Ms" );              
74
+  unsigned pitchLabelFuncId  = cmGrPageLabelFuncRegister( pgH, gvMidiSciPitchValueFunc, this, "Pitch" );
75
+
76
+  cmGrVExtSetD(&limExt,0,0,0,127);
77
+  cmGrObjSetWorldExt( cvH, cmGrRootObjH(cvH), &limExt );
78
+
79
+  cmGrObjSetWorldLimitExt(cvH, cmGrRootObjH(cvH), &limExt, kTopGrFl | kBottomGrFl );
80
+
81
+  axH = cmGrViewAxisHandle(vwH, kTopGrIdx);
82
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashMarkGrFl | kHashLabelGrFl ));
83
+
84
+  axH = cmGrViewAxisHandle(vwH, kLeftGrIdx );
85
+  cmGrAxisSetLabelFunc( axH, pitchLabelFuncId );
86
+  cmGrViewSetLabelFunc(  vwH, kLeftGrIdx, pitchLabelFuncId );
87
+  
88
+  axH = cmGrViewAxisHandle(vwH, kRightGrIdx);
89
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashLabelGrFl ));
90
+
91
+  cmGrViewSetCfg( vwH, cmSetFlag(cmGrViewCfg(vwH),kSelectHorzGrFl)  );
92
+
93
+}
94
+
95
+cmGrTksbFltk::~cmGrTksbFltk()
96
+{
97
+}
98
+
99
+void _cmGrTksbRecvScoreMsg( void* cbArg, const void* msg, unsigned msgByteCnt )
100
+{
101
+  cmGrTksbFltk* thisPtr = (cmGrTksbFltk*)cbArg;
102
+  thisPtr->recvScoreMsg(msg,msgByteCnt);
103
+}
104
+
105
+void cmGrTksbFltk::setTksbHandle( void* v )
106
+{
107
+  _tksbH.h = v;
108
+
109
+  
110
+  if( cmTakeSeqBldrIsValid(_tksbH) == false )
111
+    return;
112
+
113
+  // load the score plot objects
114
+  cmScoreSeqNotifyCb(cmTakeSeqBldrScoreHandle(_tksbH),_cmGrTksbRecvScoreMsg, this );
115
+
116
+  // get the count of score-track takes
117
+  unsigned n = cmTakeSeqBldrScTrkTakeCount(_tksbH);
118
+
119
+  // for each score-track take
120
+  for(unsigned i=0; i<n; ++i)
121
+  {
122
+    cmTksbScTrkTake_t r;
123
+
124
+    // get the ith take
125
+    if( cmTakeSeqBldrScTrkTake(_tksbH,i,&r) != kOkTsbRC )
126
+      continue;
127
+
128
+    // create the take plot-object
129
+    _insertTake(&r);
130
+  }
131
+
132
+}
133
+
134
+cmScMsgTypeId_t cmGrTksbFltk::recvScoreMsg( const void* msg, unsigned msgByteCnt )
135
+{
136
+  cmScMsg_t m;
137
+
138
+  cmScoreDecode(msg,msgByteCnt,&m);
139
+
140
+  switch( m.typeId )
141
+  {
142
+    case kBeginMsgScId:
143
+      {
144
+        _objId   = 0;
145
+        _objSecs = 0;
146
+        // remove all objects from all views
147
+        //cmGrPageClear(pageHandle());
148
+        //_srate = m.srate;
149
+        //_updateSeqMenu(m.seqCnt,m.seqId);
150
+      }
151
+      break;
152
+
153
+    case kEndMsgScId:
154
+      //size(w(),h()+1);
155
+      break;
156
+
157
+    case kEventMsgScId:
158
+      _insertEvent(&m.u.evt);
159
+      break;
160
+
161
+    case kSectionMsgScId:
162
+      _insertSection(&m.u.sect);
163
+      break;
164
+      
165
+    case kVarMsgScId:
166
+      break;
167
+
168
+    default:
169
+      { assert(0); }
170
+  }
171
+
172
+  return m.typeId;
173
+}
174
+
175
+
176
+double cmGrTksbFltk::sampleRate() const 
177
+{ 
178
+  if( cmTakeSeqBldrIsValid(_tksbH) )
179
+    return cmTakeSeqBldrSampleRate(_tksbH);
180
+  return 0;
181
+}
182
+
183
+bool cmGrTksbFltk::on_plot_object(   cmGrPlotCbArg_t* arg )
184
+{
185
+  if(  arg->selId!=kStateChangeGrPlId || cmIsNotFlag(arg->deltaFlags,kSelectGrPlFl) )
186
+    return true;
187
+
188
+  scObj_t* sop          = (scObj_t*)cmGrPlotObjUserPtr(arg->objH);
189
+  unsigned state        = cmGrPlotObjStateFlags(arg->objH);
190
+  bool     isSelectedFl = cmIsFlag( state, kSelectGrPlFl);
191
+
192
+  if( sop == NULL )
193
+    return true;
194
+
195
+  //printf("SELECT:%i %i 0x%x\n",cmGrPlotObjId(arg->objH),isSelectedFl,state);
196
+
197
+  if( sop->id==kTakeTksbId && sop->u.tlMarkerUid!=cmInvalidId )
198
+  {
199
+    if( isSelectedFl )
200
+      cmTakeSeqBldrLoadTake(_tksbH,sop->u.tlMarkerUid,true);
201
+    else
202
+      cmTakeSeqBldrUnloadTake(_tksbH,sop->u.tlMarkerUid);
203
+        
204
+    setStatusText(cmTsPrintfS("%s", cmStringNullGuard(cmTakeSeqBldrScTrkTakeText(_tksbH,sop->u.tlMarkerUid))));
205
+
206
+    _curCbTId = kRefreshTId;
207
+
208
+    // callback to: kcApp::_ctl_cb(ctl_t* cp)
209
+    callback()(this,user_data());
210
+
211
+  }
212
+
213
+  if( sop->id==kEventTksbId && sop->u.ep!=NULL && sop->u.ep->type==kBarEvtScId )
214
+  {
215
+    _lastBarPlotObjH = arg->objH;
216
+
217
+    _curCbTId = kSelectTId;
218
+
219
+    // callback to: kcApp::_ctl_cb(ctl_t* cp)
220
+    callback()(this,user_data());
221
+  }
222
+    
223
+ return true;
224
+}
225
+
226
+cmGrTksbFltk::cbTId_t cmGrTksbFltk::cbTypeId() const
227
+{  return _curCbTId;  } 
228
+
229
+unsigned cmGrTksbFltk::scoreSelectedEleIndex() const
230
+{ 
231
+
232
+  if( cmGrPlotObjIsValid(_lastBarPlotObjH) )
233
+  {
234
+    scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(_lastBarPlotObjH);
235
+
236
+    if( sop!=NULL && sop->id==kEventTksbId && sop->u.ep != NULL && sop->u.ep->type == kBarEvtScId  )
237
+    {
238
+      return sop->u.ep->locIdx;
239
+    }
240
+  }
241
+  return cmInvalidIdx;
242
+}
243
+
244
+void cmGrTksbFltk::setScoreLocation( unsigned locIdx, unsigned vel, unsigned smpIdx )
245
+{
246
+  
247
+}
248
+
249
+void cmGrTksbFltk::_insertSection( const cmScoreSection_t* m )
250
+{
251
+  // The argument is a serialzed copy of a cmScoreSection_t record.
252
+  // Convert it to a pointer to an actual object in the local score mgr.
253
+  if( cmGrPageIsValid(pageHandle()) == false )
254
+    return;
255
+
256
+  m = cmScoreSection(cmTakeSeqBldrScoreHandle(_tksbH),m->index);
257
+  assert(m!=NULL);
258
+  
259
+  const cmScoreEvt_t* ep = cmScoreEvt( cmTakeSeqBldrScoreHandle(_tksbH), m->begEvtIndex);
260
+  assert( ep != NULL );
261
+
262
+  cmGrPlH_t         plH         = plotHandle();
263
+  cmGrPgH_t         pgH         = pageHandle();
264
+  unsigned          vwIdx       = 0;
265
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
266
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
267
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
268
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
269
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
270
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
271
+  cmGrPlObjTypeId_t objTypeId   = kLineGrPlId;
272
+  cmReal_t          x           = ep->secs;
273
+  cmReal_t          y           = 120;
274
+  cmReal_t          w           = 0;
275
+  cmReal_t          h           = 7;
276
+  const cmChar_t*   label       = m->label;
277
+  unsigned          flags       = kNoDragGrPlFl;
278
+  cmGrVExt_t        wext;
279
+  scObj_t           scObj(m);
280
+  
281
+  cmGrVExtSetNull(&wext);
282
+
283
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
284
+  {
285
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on a score section.", cmStringNullGuard(label));
286
+    return;
287
+  }
288
+
289
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
290
+
291
+  unsigned f  = 0 ? (kNorthJsGrFl | kTopJsGrFl) : (kSouthJsGrFl | kBottomJsGrFl);
292
+  cmGrPlotObjSetLabelAttr( objH,  f | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, kBlackGrId );
293
+  cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kGreenGrId );
294
+  //cmGrPlotObjSetPhysExt(objH, 1, 0, 1, 0 );
295
+  cmGrPlotObjSetFontSize(objH,8);
296
+  
297
+  
298
+}
299
+
300
+void cmGrTksbFltk::_insertEvent( const cmScoreEvt_t* m )
301
+{
302
+  // The argument is a serialzed copy of a cmScoreEvt record.
303
+  // Convert it to a pointer to an actual object in the local score mgr.
304
+  if( cmGrPageIsValid(pageHandle()) == false )
305
+    return;
306
+
307
+  // Get a pointer to the score event 
308
+  m = cmScoreEvt( cmTakeSeqBldrScoreHandle(_tksbH), m->index );
309
+  assert(m!=NULL);
310
+    
311
+  cmGrPlH_t         plH         = plotHandle();
312
+  cmGrPgH_t         pgH         = pageHandle();
313
+  unsigned          vwIdx       = 0;
314
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
315
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
316
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
317
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
318
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
319
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
320
+  cmGrPlObjTypeId_t objTypeId   = kVLineGrPlId;
321
+  cmReal_t          x           = m->secs;
322
+  cmReal_t          y           = 0;
323
+  cmReal_t          w           = 0;
324
+  cmReal_t          h           = 127;
325
+  const cmChar_t*   label       = NULL;
326
+  unsigned          flags       = kNoDragGrPlFl;
327
+  int               bufN        = 7;
328
+  cmChar_t          buf[bufN+1];
329
+  cmGrVExt_t        wext;
330
+  scObj_t           scObj(m);
331
+
332
+  cmGrVExtSetNull(&wext);
333
+
334
+  switch( m->type )
335
+  {
336
+    case kNonEvtScId:
337
+      objTypeId = kRectGrPlId;
338
+      y         = m->pitch;
339
+      h         = 1;
340
+      w         = m->durSecs;
341
+      label     = cmMidiToSciPitch(m->pitch,NULL,0);
342
+      break;
343
+
344
+    case kPedalEvtScId:
345
+      objTypeId = kRectGrPlId;
346
+      y = 108;
347
+      h = 2;
348
+      w = m->durSecs;
349
+      label = "pedal";
350
+      break;
351
+
352
+    case kBarEvtScId:
353
+      {
354
+        buf[bufN] = 0;
355
+        snprintf(buf,bufN,"%i",m->barNumb);
356
+        objTypeId = kVLineGrPlId;
357
+        label     = buf;
358
+      }
359
+      break;
360
+
361
+    default:
362
+      return;
363
+  }    
364
+
365
+
366
+  // create the plot object to represent this event
367
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
368
+  {
369
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on a score event.", cmStringNullGuard(label));
370
+    return;
371
+  }
372
+
373
+  // store the score event reference as custom data inside the plot object
374
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
375
+
376
+
377
+  switch( m->type )
378
+  {
379
+    case kBarEvtScId:
380
+      {
381
+        unsigned f  = _togFl ? (kNorthJsGrFl | kTopJsGrFl) : (kSouthJsGrFl | kBottomJsGrFl);
382
+        cmGrPlotObjSetLabelAttr( objH,  f | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, kBlueGrId );
383
+        cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kYellowGrId );
384
+        cmGrPlotObjSetPhysExt(objH, 1, 0, 1, 0 );
385
+        _togFl = !_togFl;
386
+      }
387
+      break;
388
+
389
+    case kNonEvtScId:
390
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, cmGrPlotObjFillColor(objH,kEnablePlGrId) );
391
+      cmGrPlotObjSetFontSize(objH,8);
392
+      break;
393
+
394
+    case kPedalEvtScId:
395
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kDeepPinkGrId );
396
+      cmGrPlotObjSetFillColor(objH, kEnablePlGrId, kDeepPinkGrId );
397
+      cmGrPlotObjSetFontSize(objH,8);
398
+      break;
399
+
400
+    default:
401
+      break;
402
+  }
403
+
404
+  if( cmIsFlag(m->flags,kInvalidScFl) )
405
+  {
406
+    cmGrPlotObjSetFillColor(objH, kEnablePlGrId, kRedGrId );
407
+  }
408
+
409
+}
410
+
411
+void cmGrTksbFltk::_insertTake( const cmTksbScTrkTake_t* take )
412
+{
413
+
414
+  cmGrPlH_t         plH         = plotHandle();
415
+  cmGrPgH_t         pgH         = pageHandle();
416
+  unsigned          vwIdx       = 0;
417
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
418
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
419
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
420
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
421
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
422
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
423
+  cmGrPlObjTypeId_t objTypeId   = kRectGrPlId;
424
+  cmReal_t          x           = 0;
425
+  cmReal_t          y           = 0;
426
+  cmReal_t          w           = 0;
427
+  cmReal_t          h           = 127;
428
+  const cmChar_t*   label       = NULL;
429
+  unsigned          flags       = kNoDragGrPlFl | kNoFillGrPlFl;
430
+  int               bufN        = 7;
431
+  cmChar_t          buf[bufN+1];
432
+  cmGrVExt_t        wext;
433
+  cmGrVExt_t        vext;
434
+  scObj_t           scObj(take->tlMarkerUid);
435
+
436
+  cmGrVExtSetNull(&wext);
437
+
438
+  if( cmGrPlotObjIsValid(objH = _scEvtIdxToPlotObj( take->minScEvtIdx ))==false )
439
+    return;
440
+
441
+  cmGrPlotObjVExt( objH, &vext);
442
+
443
+  x = cmGrVExtMinX(&vext);
444
+  
445
+  if( cmGrPlotObjIsValid(objH = _scEvtIdxToPlotObj( take->maxScEvtIdx )) == false )
446
+    return;
447
+
448
+  cmGrPlotObjVExt( objH, &vext);
449
+
450
+  w = cmGrVExtMaxX(&vext) - x;
451
+  h = 1;
452
+  y = _nextTakeY;
453
+
454
+
455
+  buf[bufN] = 0;
456
+  snprintf(buf,bufN,"%i",(_nextTakeY-5)/2);
457
+  label     = buf;
458
+
459
+  _nextTakeY += 2;
460
+  if( _nextTakeY > 120 )
461
+    _nextTakeY = 5;
462
+  
463
+  // create the plot object to represent this event
464
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
465
+  {
466
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on score-track take.", cmStringNullGuard(label));
467
+    return;
468
+  }
469
+
470
+  // store the score event reference as custom data inside the plot object
471
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
472
+
473
+
474
+  cmGrPlotObjSetLineColor( objH, kFocusPlGrId,  kRedGrId );
475
+  cmGrPlotObjSetLineColor( objH, kSelectPlGrId, kDeepPinkGrId );
476
+  cmGrPlotObjSetFontSize(objH,8);
477
+
478
+}
479
+
480
+#define cmMENU_TITLE "Bldr"
481
+void cmGrTksbFltk::_createMenu( )
482
+{
483
+  int idx = _menuBar->add(cmMENU_TITLE,0,NULL,0,FL_SUBMENU);
484
+  const char* titleArray[] = { "Pitch", "Attributes", "Dynamics", "Location", "Fraction", "Section Even", "Section Dyn", "Section Tempo" };
485
+  bool        onFl[]       = { true,     false,        false,     false,       false,     false,          false,         false };
486
+  int i;
487
+  for(i=0; i<kMenuItemCnt; ++i)
488
+  {
489
+    _menuArray[i].id = i;
490
+    _menuArray[i].p  = this;
491
+    _menuBar->insert(idx+1+i,titleArray[i],0,_s_menuCallback, _menuArray + i, FL_MENU_TOGGLE );  
492
+
493
+    if( onFl[i] )
494
+    {
495
+      Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + idx + i + 1;
496
+      mip->set();
497
+    }
498
+  }
499
+
500
+  _menuBar->redraw();
501
+
502
+}
503
+
504
+bool cmGrTksbFltk::_isMenuChecked( int id )
505
+{
506
+  unsigned i;
507
+  // locate the menu item assoc'd with id
508
+  for(i=0; i<kMenuItemCnt; ++i)
509
+    if( _menuArray[i].id == id )
510
+      break;
511
+
512
+  assert( i < kMenuItemCnt );
513
+
514
+  int menuIdx;
515
+  if(( menuIdx = _menuBar->find_index(cmMENU_TITLE)) == -1 )
516
+    return false;
517
+  
518
+  // The menu items and _menuArray[] were initialized in the same order
519
+  // therefore the offset from the base of both should be the same.
520
+  Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + menuIdx + i + 1;
521
+
522
+  assert( (item_t*)mip->user_data() == _menuArray + i );
523
+
524
+  return mip->value() != 0;
525
+}
526
+
527
+void cmGrTksbFltk::_setEventLabels()
528
+{
529
+  enum { kPitchFl=0x01, kAttrFl=0x02, kDynFl=0x04, kLocFl=0x08, kFracFl };
530
+ 
531
+  cmGrPlH_t plH = plotHandle();
532
+  unsigned flags = 0;
533
+  flags |= _isMenuChecked(kPitchMId)  ? kPitchFl : 0;
534
+  flags |= _isMenuChecked(kAttrMId)   ? kAttrFl  : 0;
535
+  flags |= _isMenuChecked(kDynMId)    ? kDynFl   : 0;
536
+  flags |= _isMenuChecked(kLocIdxMId) ? kLocFl   : 0;
537
+  flags |= _isMenuChecked(kFracMId)   ? kFracFl  : 0;
538
+ 
539
+  unsigned n = cmGrPlotObjectCount(plH);
540
+  unsigned i;
541
+  for(i=0; i<n; ++i)
542
+  {
543
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
544
+
545
+    if( cmGrPlotObjIsValid(poH) )
546
+    {
547
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
548
+      
549
+      if( sop!=NULL && sop->id==kEventTksbId && sop->u.ep!=NULL && sop->u.ep->type==kNonEvtScId )
550
+      {
551
+        const cmScoreEvt_t* ep   = sop->u.ep;
552
+        int           bufN = 255;
553
+        cmChar_t buf[ bufN+1 ];
554
+
555
+        buf[bufN] = 0;
556
+        buf[0]    = 0;
557
+
558
+        if( cmIsFlag(flags,kPitchFl) )
559
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",cmMidiToSciPitch(ep->pitch,NULL,0));
560
+
561
+        if( cmIsFlag(flags,kAttrFl) )
562
+        {
563
+          cmChar_t s[4]; 
564
+          int      j=0;
565
+          if( cmIsFlag(ep->flags,kEvenScFl) )
566
+            s[j++] = 'e';
567
+          if( cmIsFlag(ep->flags,kDynScFl) )
568
+            s[j++] = 'd';
569
+          if( cmIsFlag(ep->flags,kTempoScFl) )
570
+            s[j++] = 't';
571
+          s[j] = 0;
572
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",s);
573
+        }
574
+      
575
+
576
+        if( cmIsFlag(flags,kDynFl) && cmIsFlag(ep->flags,kDynScFl) )
577
+        {
578
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"d:%i",ep->dynVal);
579
+
580
+          if( ep->perfDynLvl != 0 )
581
+            snprintf(buf+strlen(buf),bufN-strlen(buf),"|%i ",ep->perfDynLvl);
582
+          else
583
+            snprintf(buf+strlen(buf),bufN-strlen(buf)," ");
584
+        }
585
+
586
+        if( cmIsFlag(flags,kLocFl) )
587
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"loc:%i ",ep->locIdx);
588
+
589
+        if( cmIsFlag(flags,kFracFl) && ep->frac != 0)
590
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"%5.3f ",ep->frac);
591
+
592
+        cmGrPlotObjSetLabel(poH, buf );
593
+      }
594
+    }
595
+  }
596
+}
597
+
598
+void cmGrTksbFltk::_setSectionLabels()
599
+{
600
+ enum { kEvenFl=0x01, kDynFl=0x02, kTempoFl=0x04 };
601
+ 
602
+  cmGrPlH_t plH = plotHandle();
603
+  unsigned flags = 0;
604
+  flags |= _isMenuChecked(kSectEvenMId)  ? kEvenFl  : 0;
605
+  flags |= _isMenuChecked(kSectDynMId)   ? kDynFl   : 0;
606
+  flags |= _isMenuChecked(kSectTempoMId) ? kTempoFl : 0;
607
+ 
608
+  unsigned n = cmGrPlotObjectCount(plH);
609
+  unsigned i;
610
+  for(i=0; i<n; ++i)
611
+  {
612
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
613
+
614
+    if( cmGrPlotObjIsValid(poH) )
615
+    {
616
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
617
+      
618
+      if( sop!=NULL && sop->id==kSectionTksbId && sop->u.sp!=NULL )
619
+      {
620
+        const cmScoreSection_t* sp   = sop->u.sp;
621
+        int           bufN = 255;
622
+        cmChar_t buf[ bufN+1 ];
623
+
624
+        buf[bufN] = 0;
625
+        buf[0]    = 0;
626
+
627
+        snprintf(buf,bufN,"%s ",sp->label);
628
+
629
+        if( cmIsFlag(flags,kEvenFl) && sp->vars[kEvenVarScId] != DBL_MAX)
630
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"e:%f ",sp->vars[kEvenVarScId]);
631
+
632
+        if( cmIsFlag(flags,kDynFl)  && sp->vars[kDynVarScId] != DBL_MAX)
633
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"d:%f ",sp->vars[kDynVarScId]);
634
+
635
+        if( cmIsFlag(flags,kTempoFl)  && sp->vars[kTempoVarScId] != DBL_MAX)
636
+          snprintf(buf+strlen(buf),bufN-strlen(buf),"t:%f ",sp->vars[kTempoVarScId]);
637
+               
638
+        cmGrPlotObjSetLabel(poH, buf );
639
+      }
640
+    }
641
+  }
642
+   
643
+}
644
+
645
+void cmGrTksbFltk::_s_menuCallback(Fl_Widget* w, void* arg )
646
+{
647
+  item_t*          ip = (item_t*)arg;
648
+  cmGrTksbFltk*    p  = ip->p;
649
+  unsigned long    id = ip->id;
650
+
651
+  switch( id )
652
+  {
653
+    case kPitchMId:
654
+    case kAttrMId:
655
+    case kDynMId:
656
+    case kLocIdxMId:
657
+    case kFracMId:
658
+      {
659
+        p->_setEventLabels();
660
+        p->redraw();
661
+      }
662
+      break;
663
+
664
+    case kSectEvenMId:
665
+    case kSectDynMId:
666
+    case kSectTempoMId:
667
+      {
668
+        p->_setSectionLabels();
669
+        p->redraw();
670
+      }
671
+      break;
672
+  }
673
+}
674
+
675
+cmGrPlObjH_t cmGrTksbFltk::_scEvtIdxToPlotObj( unsigned scEvtIdx )
676
+{
677
+  cmGrPlH_t    plH = plotHandle();
678
+  unsigned     n   = cmGrPlotObjectCount(plH); 
679
+  unsigned     i;
680
+  cmGrPlObjH_t poH;
681
+  scObj_t*     sop;
682
+ 
683
+  for(i=0; i<n; ++i)
684
+    if(cmGrPlotObjIsValid(poH = cmGrPlotObjectIndexToHandle(plH,i))
685
+      && (sop = (scObj_t*)cmGrPlotObjUserPtr(poH)) != NULL 
686
+      && sop->id                                   == kEventTksbId 
687
+      && sop->u.ep->index                          == scEvtIdx )
688
+    {
689
+      return poH;
690
+    }
691
+    
692
+  
693
+  return cmGrPlObjNullHandle;
694
+} 
695
+

+ 110
- 0
src/tlCtl/cmGrTksbFltk.h View File

@@ -0,0 +1,110 @@
1
+#ifndef cmGrTksbFltk_h
2
+#define cmGrTksbFltk_h
3
+
4
+class Fl_Menu_Bar;
5
+class cmdIf;
6
+
7
+class cmGrTksbFltk : public cmGrPlotFltk, public gvHashFuncArg
8
+{
9
+ public:
10
+  cmGrTksbFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menuBar, int x, int y, int w, int h);
11
+  virtual ~cmGrTksbFltk();
12
+
13
+  void setTksbHandle( void* vp );
14
+
15
+  virtual cmScMsgTypeId_t recvScoreMsg( const void* msg, unsigned msgByteCnt );
16
+
17
+  virtual double sampleRate() const;
18
+
19
+  virtual bool on_plot_object( cmGrPlotCbArg_t* arg );
20
+
21
+  typedef enum
22
+  {
23
+    kInvalidTId,
24
+    kSelectTId,
25
+    kRefreshTId,
26
+  } cbTId_t;
27
+
28
+  cbTId_t cbTypeId() const;
29
+
30
+  virtual unsigned scoreSelectedEleIndex() const;
31
+
32
+  virtual void setScoreLocation( unsigned locIdx, unsigned vel, unsigned smpIdx );
33
+
34
+ private:
35
+  enum
36
+  {
37
+    kOkRC,
38
+    kInsertObjFailRC
39
+  };
40
+
41
+  enum
42
+  {
43
+    kPitchMId,
44
+    kAttrMId,
45
+    kDynMId,
46
+    kLocIdxMId,
47
+    kFracMId,
48
+    kSectEvenMId,
49
+    kSectDynMId,
50
+    kSectTempoMId,
51
+    kMenuItemCnt
52
+  };
53
+
54
+  typedef struct
55
+  {
56
+    cmGrTksbFltk* p;
57
+    int           id;
58
+  } item_t;
59
+
60
+  typedef enum
61
+  {
62
+    kEventTksbId,
63
+    kSectionTksbId,
64
+    kTakeTksbId
65
+  } tksbId_t;
66
+
67
+  typedef struct scObj_str
68
+  {
69
+    tksbId_t id; 
70
+    union
71
+    {
72
+      const cmScoreEvt_t*     ep;
73
+      const cmScoreSection_t* sp;
74
+      unsigned                tlMarkerUid;
75
+    } u;
76
+
77
+    scObj_str( const cmScoreEvt_t* e)     : id(kEventTksbId)    { u.ep=e;}
78
+    scObj_str( const cmScoreSection_t* s) : id(kSectionTksbId)  { u.sp=s;}
79
+    scObj_str( unsigned i )               : id(kTakeTksbId)     { u.tlMarkerUid=i;}
80
+  } scObj_t;
81
+
82
+  cmErr_t          _err;
83
+  //cmdIf*           _cmdIf;
84
+  cmTakeSeqBldrH_t _tksbH;
85
+  Fl_Menu_Bar*     _menuBar;
86
+  unsigned         _samplesMetricId;
87
+  unsigned         _secondsMetricId;
88
+  double           _objSecs;
89
+  unsigned         _objId;
90
+  bool             _togFl; 
91
+  cmGrPlObjH_t     _lastBarPlotObjH;
92
+  item_t           _menuArray[ kMenuItemCnt ];
93
+  unsigned         _nextTakeY;
94
+  cbTId_t          _curCbTId;
95
+
96
+  void _insertSection( const cmScoreSection_t* s );
97
+  void _insertEvent( const cmScoreEvt_t* m );
98
+  void _insertTake( const cmTksbScTrkTake_t* take );
99
+  void _createMenu();
100
+  bool _isMenuChecked( int id );
101
+  void _setEventLabels();
102
+  void _setSectionLabels();
103
+  cmGrPlObjH_t _scEvtIdxToPlotObj( unsigned scEvtIdx );
104
+
105
+  static void _s_menuCallback(Fl_Widget* w, void* arg);
106
+  
107
+};
108
+
109
+
110
+#endif

+ 461
- 0
src/tlCtl/cmGrTksrFltk.cpp View File

@@ -0,0 +1,461 @@
1
+#include <FL/Fl.H>
2
+#include <Fl/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+#include <Fl/Fl_Menu_Bar.H>
7
+
8
+#include <vector>
9
+
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmGlobal.h"
13
+#include "cmFloatTypes.h"
14
+#include "cmRpt.h"
15
+#include "cmErr.h"
16
+#include "cmCtx.h"
17
+#include "cmMem.h"
18
+#include "cmMallocDebug.h"
19
+#include "cmLinkedHeap.h"
20
+#include "cmText.h"
21
+#include "cmThread.h"
22
+#include "cmPrefs.h"
23
+#include "cmSymTbl.h"
24
+#include "cmTime.h"
25
+#include "cmMidi.h"
26
+#include "cmMidiFile.h"
27
+#include "cmAudioFile.h"
28
+#include "cmAudioFileMgr.h"
29
+#include "cmTimeLine.h"
30
+#include "cmScore.h"
31
+#include "cmTakeSeqBldr.h"
32
+
33
+#include "cmGr.h"
34
+#include "cmGrDevCtx.h"
35
+#include "cmGrPlot.h"
36
+#include "cmGrPage.h"
37
+#include "cmGrFltk.h"
38
+#include "gvHashFunc.h"
39
+#include "cmGrTksrFltk.h"
40
+#include "cmGrPlotAudio.h"
41
+#include "cmdIf.h"
42
+
43
+cmGrTksrFltk::cmGrTksrFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menu, int x, int y, int w, int h)
44
+  : cmGrPlotFltk(ctx,x,y,w,h),
45
+    //_cmdIf(cp),
46
+  _tksbH(cmTakeSeqBldrNullHandle),
47
+    _menuBar(menu),
48
+  _samplesMetricId(cmInvalidId),_secondsMetricId(cmInvalidId),
49
+    //_objSecs(0),
50
+    _objId(0)
51
+    //_togFl(true)
52
+{
53
+  cmErrSetup(&_err,&ctx->rpt,"cmGrTksrFltk");
54
+
55
+  _createMenu();
56
+
57
+  if( cmGrPageIsValid(pageHandle()) == false )
58
+    return;
59
+
60
+  initViews(1,1);
61
+
62
+  unsigned   vwIdx = 0;
63
+  cmGrPgH_t  pgH   = pageHandle();
64
+  cmGrVwH_t  vwH   = cmGrPageViewHandle( pgH, vwIdx);
65
+  cmGrH_t    cvH   = cmGrViewGrHandle( vwH );
66
+  cmGrAxH_t  axH   = cmGrAxNullHandle;
67
+  cmGrVExt_t limExt;
68
+
69
+  _samplesMetricId = cmGrPageLabelFuncRegister( pgH, gvRoundHashValueFunc,    this, "Round" );              
70
+  _secondsMetricId = cmGrPageLabelFuncRegister( pgH, gvMinSecMsHashValueFunc, this, "Min:Sec:Ms" );              
71
+  unsigned pitchLabelFuncId  = cmGrPageLabelFuncRegister( pgH, gvMidiSciPitchValueFunc, this, "Pitch" );
72
+
73
+  cmGrVExtSetD(&limExt,0,0,0,127);
74
+  cmGrObjSetWorldExt( cvH, cmGrRootObjH(cvH), &limExt );
75
+
76
+  cmGrObjSetWorldLimitExt(cvH, cmGrRootObjH(cvH), &limExt, kTopGrFl | kBottomGrFl );
77
+
78
+  axH = cmGrViewAxisHandle(vwH, kTopGrIdx);
79
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashMarkGrFl | kHashLabelGrFl ));
80
+
81
+  axH = cmGrViewAxisHandle(vwH, kLeftGrIdx );
82
+  cmGrAxisSetLabelFunc( axH, pitchLabelFuncId );
83
+  cmGrViewSetLabelFunc(  vwH, kLeftGrIdx, pitchLabelFuncId );
84
+  
85
+  axH = cmGrViewAxisHandle(vwH, kRightGrIdx);
86
+  cmGrAxisSetCfg( axH, cmClrFlag(cmGrAxisCfg( axH ), kHashLabelGrFl ));
87
+
88
+  cmGrViewSetCfg( vwH, cmSetFlag(cmGrViewCfg(vwH),kSelectHorzGrFl)  );
89
+
90
+}
91
+
92
+cmGrTksrFltk::~cmGrTksrFltk()
93
+{}
94
+
95
+
96
+void cmGrTksrFltk::setTksbHandle( void* v )
97
+{
98
+  _tksbH.h = v;
99
+}
100
+
101
+void cmGrTksrFltk::refresh()
102
+{
103
+  if( cmGrPlotClear( plotHandle() ) != kOkGrPlRC )
104
+  {
105
+    cmErrMsg(&_err,kClearPlotFailRC,"Plot clear failed.");
106
+    return;
107
+  }
108
+
109
+  if( cmTakeSeqBldrIsValid(_tksbH) == false )
110
+    return;
111
+
112
+  // insert tksb events here
113
+  cmTakeSeqBldrRendReset(_tksbH);
114
+
115
+  cmTksbRend_t m;
116
+  unsigned absSmpIdx = 0;
117
+  double   srate     = cmTakeSeqBldrSampleRate(_tksbH);
118
+  while( cmTakeSeqBldrRendNext(_tksbH,&m) )
119
+  {
120
+    m.evt.smpIdx = absSmpIdx;
121
+    _insertEvent(&m,srate);
122
+    absSmpIdx += m.offsetSmp;
123
+  } 
124
+}
125
+
126
+double cmGrTksrFltk::sampleRate() const
127
+{
128
+  if( cmTakeSeqBldrIsValid(_tksbH)  )
129
+    return cmTakeSeqBldrSampleRate(_tksbH);
130
+  return 0;
131
+}
132
+
133
+bool cmGrTksrFltk::on_plot_object(   cmGrPlotCbArg_t* arg )
134
+{
135
+  /*
136
+  if(  arg->selId==kStateChangeGrPlId && cmIsFlag(arg->deltaFlags,kSelectGrPlFl) )
137
+  {
138
+    scObj_t* sop          = (scObj_t*)cmGrPlotObjUserPtr(arg->objH);
139
+    unsigned state        = cmGrPlotObjStateFlags(arg->objH);
140
+    bool     isSelectedFl = cmIsFlag( state, kSelectGrPlFl);
141
+
142
+    if( sop != NULL )
143
+    {
144
+
145
+      //printf("SELECT:%i %i 0x%x\n",cmGrPlotObjId(arg->objH),isSelectedFl,state);
146
+
147
+      if( sop->id==kTakeTksrId && sop->u.tlMarkerUid!=cmInvalidId )
148
+      {
149
+        if( isSelectedFl )
150
+          cmTakeSeqBldrLoadTake(_tksbH,sop->u.tlMarkerUid,true);
151
+        else
152
+          cmTakeSeqBldrUnloadTake(_tksbH,sop->u.tlMarkerUid);
153
+        
154
+        setStatusText(cmTsPrintfS("%s", cmStringNullGuard(cmTakeSeqBldrScTrkTakeText(_tksbH,sop->u.tlMarkerUid))));
155
+      }
156
+
157
+      if( sop->id==kEventTksrId && sop->u.ep!=NULL && sop->u.ep->type==kBarEvtScId )
158
+      {
159
+        _lastBarPlotObjH = arg->objH;
160
+
161
+        // callback to: kcApp::_ctl_cb(ctl_t* cp)
162
+        callback()(this,user_data());
163
+      }
164
+    }
165
+
166
+    
167
+  }
168
+  */
169
+  return true;
170
+}
171
+
172
+
173
+void cmGrTksrFltk::_insertEvent( const cmTksbRend_t* m, double srate )
174
+{
175
+  if( cmGrPageIsValid(pageHandle()) == false )
176
+    return;
177
+
178
+  cmGrPlH_t         plH         = plotHandle();
179
+  cmGrPgH_t         pgH         = pageHandle();
180
+  unsigned          vwIdx       = 0;
181
+  cmGrVwH_t         vwH         = cmGrPageViewHandle(   pgH, vwIdx );
182
+  cmGrH_t           cvH         = cmGrViewGrHandle( vwH );
183
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
184
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
185
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
186
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
187
+  cmGrPlObjTypeId_t objTypeId   = kRectGrPlId;
188
+  cmReal_t          x           = m->evt.smpIdx / srate;
189
+  cmReal_t          y           = 0;
190
+  cmReal_t          h           = 1;
191
+  cmReal_t          w           = m->durSmp / srate;
192
+  const cmChar_t*   label       = NULL;
193
+  unsigned          flags       = kNoDragGrPlFl;
194
+  tksrId_t          tid         = kInvalidTksrId;
195
+
196
+
197
+  if( cmMidiIsNoteOn(m->evt.status) )
198
+  {
199
+    tid    = kNoteTksrId;
200
+    y      = m->evt.d0;
201
+    label  = cmMidiToSciPitch(m->evt.d0,NULL,0);
202
+  }
203
+  else
204
+  {
205
+    if( cmMidiIsPedalDown(m->evt.status,m->evt.d0,m->evt.d1) )
206
+    {
207
+      tid   = kPedalTksrId;
208
+      y     = 120;
209
+      label = cmMidiPedalLabel(m->evt.d0);
210
+      flags |= kNoFillGrPlFl;
211
+    }
212
+  }
213
+
214
+  if( tid == kInvalidTksrId )
215
+    return;
216
+
217
+  //printf("absSmpIdx:%f %f\n",x,w);
218
+
219
+
220
+  // create the plot object to represent this event
221
+  if( cmGrPlotObjCreate(plH, cvH, &objH, _objId++, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, NULL ) != kOkGrPlRC )
222
+  {
223
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on a score event.", cmStringNullGuard(label));
224
+    return;
225
+  }
226
+
227
+  // store the score event reference as custom data inside the plot object
228
+  scObj_t  scObj(tid,m->rid);
229
+  cmGrPlotObjAllocUser(objH,&scObj,sizeof(scObj));
230
+
231
+
232
+  switch( tid )
233
+  {
234
+    case kNoteTksrId:
235
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, cmGrPlotObjFillColor(objH,kEnablePlGrId) );
236
+      cmGrPlotObjSetFontSize(objH,8);
237
+      break;
238
+
239
+    case kPedalTksrId:
240
+      cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kDeepPinkGrId );
241
+      cmGrPlotObjSetFontSize(objH,8);
242
+      break;
243
+
244
+    default:
245
+      break;
246
+  }
247
+
248
+
249
+}
250
+
251
+#define cmMENU_TITLE "Rndr"
252
+void cmGrTksrFltk::_createMenu( )
253
+{
254
+  int idx = _menuBar->add(cmMENU_TITLE,0,NULL,0,FL_SUBMENU);
255
+  const char* titleArray[] = { "Pitch", "ScEvtIdx", "Delete", "Sustain", "Sostenuto", "Write", "Read" };
256
+  bool        onFl[]       = { true,     false,      false,     false,     false,       false,   false };
257
+  bool        checkFl[]    = { true,     true,       false,     false,     false,       false,   false }; 
258
+  int i;
259
+  for(i=0; i<kMenuItemCnt; ++i)
260
+  {
261
+    _menuArray[i].id = i;
262
+    _menuArray[i].p  = this;
263
+    _menuBar->insert(idx+1+i,titleArray[i],0,_s_menuCallback, _menuArray + i, checkFl[i] ? FL_MENU_TOGGLE : 0 );  
264
+
265
+    if( onFl[i] )
266
+    {
267
+      Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + idx + i + 1;
268
+      mip->set();
269
+    }
270
+  }
271
+
272
+  _menuBar->redraw();
273
+
274
+}
275
+
276
+bool cmGrTksrFltk::_isMenuChecked( int id )
277
+{
278
+  unsigned i;
279
+  // locate the menu item assoc'd with id
280
+  for(i=0; i<kMenuItemCnt; ++i)
281
+    if( _menuArray[i].id == id )
282
+      break;
283
+
284
+  assert( i < kMenuItemCnt );
285
+
286
+  int menuIdx;
287
+  if(( menuIdx = _menuBar->find_index(cmMENU_TITLE)) == -1 )
288
+    return false;
289
+  
290
+  // The menu items and _menuArray[] were initialized in the same order
291
+  // therefore the offset from the base of both should be the same.
292
+  Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + menuIdx + i + 1;
293
+
294
+  assert( (item_t*)mip->user_data() == _menuArray + i );
295
+
296
+  return mip->value() != 0;
297
+}
298
+
299
+void cmGrTksrFltk::_setEventLabels()
300
+{
301
+  enum { kPitchFl=0x01, kScEvtFl=0x02 };
302
+ 
303
+  if( cmTakeSeqBldrIsValid( _tksbH ) == false )
304
+    return;
305
+
306
+  cmGrPlH_t plH = plotHandle();
307
+  unsigned flags = 0;
308
+  flags |= _isMenuChecked(kPitchMId)  ? kPitchFl : 0;
309
+  flags |= _isMenuChecked(kScEvtMId)  ? kScEvtFl : 0;
310
+ 
311
+  unsigned n = cmGrPlotObjectCount(plH);
312
+  unsigned i;
313
+  for(i=0; i<n; ++i)
314
+  {
315
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
316
+
317
+    if( cmGrPlotObjIsValid(poH) )
318
+    {
319
+      scObj_t* sop = (scObj_t*)cmGrPlotObjUserPtr(poH);
320
+      
321
+      if( sop!=NULL && sop->id==kNoteTksrId && sop->u.rid!=cmInvalidId )
322
+      {
323
+        cmTksbRend_t r;
324
+
325
+        if( cmTakeSeqBldrRendInfo( _tksbH, sop->u.rid, &r ) == kOkTsbRC )
326
+        {
327
+
328
+          int      bufN = 255;
329
+          cmChar_t buf[ bufN+1 ];
330
+
331
+          buf[bufN] = 0;
332
+          buf[0]    = 0;
333
+
334
+          if( cmIsFlag(flags,kPitchFl) && r.evt.status == kNoteOnMdId )
335
+            snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",cmMidiToSciPitch(r.evt.d0,NULL,0));
336
+
337
+          if( cmIsFlag(flags,kScEvtFl) && r.scEvtIdx != cmInvalidIdx )
338
+            snprintf(buf+strlen(buf),bufN-strlen(buf),"sei:%i ",r.scEvtIdx);
339
+
340
+          cmGrPlotObjSetLabel(poH, buf );
341
+        }
342
+      }
343
+    }
344
+  }
345
+}
346
+
347
+
348
+void cmGrTksrFltk::_s_deleteSelectedEle( void* arg, cmGrPlObjH_t oh )
349
+{
350
+  if( cmIsFlag(cmGrPlotObjStateFlags(oh), kSelectGrPlFl) )
351
+  {
352
+    cmGrTksrFltk* p = (cmGrTksrFltk*)arg;
353
+    scObj_t* sop   = (scObj_t*)cmGrPlotObjUserPtr(oh);
354
+    cmTakeSeqBldrRendDelete( p->_tksbH, sop->u.rid );
355
+  }
356
+}
357
+
358
+void cmGrTksrFltk::_write()
359
+{
360
+  const cmChar_t* fn = "/home/kevin/temp/kr/tksb/tksb0.js";
361
+
362
+  if( cmTakeSeqBldrIsValid(_tksbH) == false )
363
+    return;
364
+
365
+  if( cmTakeSeqBldrWrite( _tksbH, fn ) != kOkTsbRC )
366
+    cmErrMsg(&_err,kTksbFailRC,"Render write failed for '%s'.",cmStringNullGuard(fn));
367
+
368
+}
369
+
370
+void cmGrTksrFltk::_read()
371
+{
372
+  const cmChar_t* fn = "/home/kevin/temp/kr/tksb/tksb0.js";
373
+
374
+  if( cmTakeSeqBldrIsValid(_tksbH) == false )
375
+    return;
376
+
377
+  if( cmTakeSeqBldrRead( _tksbH, fn ) != kOkTsbRC )
378
+    cmErrMsg(&_err,kTksbFailRC,"Render write failed for '%s'.",cmStringNullGuard(fn)); 
379
+}
380
+
381
+void cmGrTksrFltk::_insertPedal( unsigned long pedalMId )
382
+{
383
+  if( cmTakeSeqBldrIsValid(_tksbH) == false )
384
+    return;
385
+
386
+  unsigned   vwIdx = 0;
387
+  cmGrPgH_t  pgH   = pageHandle();
388
+  cmGrVwH_t  vwH   = cmGrPageViewHandle( pgH, vwIdx);
389
+  cmGrH_t    cvH   = cmGrViewGrHandle( vwH );
390
+  double    srate  = cmTakeSeqBldrSampleRate(_tksbH);
391
+  cmGrVPt_t  pt0,pt1;
392
+  unsigned rid;
393
+  cmTksbEvent_t e;
394
+  memset(&e,0,sizeof(e));
395
+
396
+  cmGrSelectPoints( cvH, &pt0, &pt1 );
397
+
398
+  unsigned durSmp = (pt1.x - pt0.x) * srate;
399
+
400
+  e.status = kCtlMdId;
401
+  switch( pedalMId )
402
+  {
403
+    case kSustainMId:
404
+      e.d0 = kSustainCtlMdId;
405
+      break;
406
+
407
+    case kSostenutoMId:
408
+      e.d0 = kSostenutoCtlMdId;
409
+      break;
410
+  }
411
+
412
+  //printf("x0:%f x1:%f %i\n",pt0.x,pt1.x,durSmp);
413
+
414
+  e.smpIdx = pt0.x * srate;
415
+  e.d1     = 127;
416
+  cmTakeSeqBldrRendInsert( _tksbH, &e, durSmp, &rid );
417
+
418
+  e.smpIdx = pt1.x * srate;
419
+  e.d1     = 0;
420
+  cmTakeSeqBldrRendInsert( _tksbH, &e, 0, &rid );
421
+
422
+  refresh();
423
+}
424
+
425
+void cmGrTksrFltk::_s_menuCallback(Fl_Widget* w, void* arg )
426
+{
427
+  item_t*          ip = (item_t*)arg;
428
+  cmGrTksrFltk*    p  = ip->p;
429
+  unsigned long    id = ip->id;
430
+
431
+  switch( id )
432
+  {
433
+    case kPitchMId:
434
+    case kScEvtMId:
435
+      p->_setEventLabels();      
436
+      p->redraw();
437
+      break;
438
+    
439
+    case kDeleteMId:
440
+      cmGrPlotObjCb(p->plotHandle(),_s_deleteSelectedEle,p);
441
+      p->refresh();
442
+      p->redraw();
443
+      break;
444
+
445
+    case kSustainMId:
446
+    case kSostenutoMId:
447
+      p->_insertPedal(id);
448
+      p->refresh();
449
+      p->redraw();
450
+      break;
451
+
452
+    case kWriteMId:
453
+      p->_write();
454
+      break;
455
+
456
+    case kReadMId:
457
+      p->_read();
458
+      break;
459
+  }
460
+}
461
+

+ 91
- 0
src/tlCtl/cmGrTksrFltk.h View File

@@ -0,0 +1,91 @@
1
+#ifndef cmGrTksrFltk_h
2
+#define cmGrTksrFltk_h
3
+
4
+class Fl_Menu_Bar;
5
+class cmdIf;
6
+
7
+class cmGrTksrFltk : public cmGrPlotFltk, public gvHashFuncArg
8
+{
9
+ public:
10
+  cmGrTksrFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menuBar, int x, int y, int w, int h);
11
+  virtual ~cmGrTksrFltk();
12
+
13
+  void setTksbHandle( void* vp );
14
+
15
+  void refresh();
16
+
17
+  virtual double sampleRate() const;
18
+
19
+  virtual bool on_plot_object( cmGrPlotCbArg_t* arg );
20
+
21
+ private:
22
+  enum
23
+  {
24
+    kOkRC,
25
+    kInsertObjFailRC,
26
+    kClearPlotFailRC,
27
+    kTksbFailRC
28
+  };
29
+
30
+  enum
31
+  {
32
+    kPitchMId,
33
+    kScEvtMId,
34
+    kDeleteMId,
35
+    kSustainMId,
36
+    kSostenutoMId,
37
+    kWriteMId,
38
+    kReadMId,
39
+    kMenuItemCnt
40
+  };
41
+
42
+  typedef struct
43
+  {
44
+    cmGrTksrFltk* p;
45
+    int           id;
46
+  } item_t;
47
+
48
+  typedef enum
49
+  {
50
+    kInvalidTksrId,
51
+    kNoteTksrId,
52
+    kPedalTksrId,
53
+  } tksrId_t;
54
+
55
+  typedef struct scObj_str
56
+  {
57
+    tksrId_t id; 
58
+    union
59
+    {
60
+      unsigned rid;
61
+    } u;
62
+
63
+    scObj_str( tksrId_t i, unsigned rid ) : id(i) { u.rid=rid; }
64
+  } scObj_t;
65
+
66
+  cmErr_t          _err;
67
+  //cmdIf*           _cmdIf;
68
+  cmTakeSeqBldrH_t _tksbH;
69
+  Fl_Menu_Bar*     _menuBar;
70
+  unsigned         _samplesMetricId;
71
+  unsigned         _secondsMetricId;
72
+  //double           _objSecs;
73
+  unsigned         _objId;
74
+  //bool             _togFl; 
75
+  item_t           _menuArray[ kMenuItemCnt ];
76
+
77
+  void _insertEvent( const cmTksbRend_t* m, double srate );
78
+  void _createMenu();
79
+  bool _isMenuChecked( int id );
80
+  void _setEventLabels();
81
+  void _write();
82
+  void _read();
83
+  void _insertPedal( unsigned long pedalMId );
84
+
85
+  static void _s_deleteSelectedEle( void* arg, cmGrPlObjH_t oh );
86
+  static void _s_menuCallback(Fl_Widget* w, void* arg);
87
+  
88
+};
89
+
90
+
91
+#endif

+ 835
- 0
src/tlCtl/cmGrTlFltk.cpp View File

@@ -0,0 +1,835 @@
1
+#include <FL/Fl.H>
2
+#include <Fl/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+#include <Fl/Fl_Menu_Bar.H>
7
+
8
+#include <vector>
9
+
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmGlobal.h"
13
+#include "cmFloatTypes.h"
14
+#include "cmRpt.h"
15
+#include "cmErr.h"
16
+#include "cmCtx.h"
17
+#include "cmMem.h"
18
+#include "cmMallocDebug.h"
19
+#include "cmLinkedHeap.h"
20
+#include "cmText.h"
21
+#include "cmThread.h"
22
+#include "cmPrefs.h"
23
+#include "cmTime.h"
24
+#include "cmMidi.h"
25
+#include "cmMidiFile.h"
26
+#include "cmAudioFile.h"
27
+#include "cmAudioFileMgr.h"
28
+#include "cmSymTbl.h"
29
+#include "cmTimeLine.h"
30
+#include "cmScore.h"
31
+
32
+#include "cmGr.h"
33
+#include "cmGrDevCtx.h"
34
+#include "cmGrPlot.h"
35
+#include "cmGrPage.h"
36
+#include "cmGrFltk.h"
37
+
38
+#include "gvHashFunc.h"
39
+#include "cmGrTlFltk.h"
40
+#include "cmGrPlotAudio.h"
41
+#include "cmdIf.h"
42
+
43
+
44
+
45
+cmGrTlFltk::cmGrTlFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menu, int x, int y, int w, int h)
46
+  : cmGrPlotFltk(ctx,x,y,w,h),_srate(0),_cmdIf(cp),_menuBar(menu),
47
+    _seqMenuIdx(cmInvalidIdx),_seqCnt(0),_seqItemArray(NULL),
48
+    _markCnt(0),
49
+    _samplesMetricId(cmInvalidId),_secondsMetricId(cmInvalidId),
50
+    _selMarkPlotObjH(cmGrPlObjNullHandle),
51
+    _curSeqId(cmInvalidId)
52
+{
53
+  _createMenu();
54
+  //_seqMenuIdx = _menuBar->find_index("&Seq");
55
+
56
+  cmErrSetup(&_err,&ctx->rpt,"cmGrTlFltk");
57
+
58
+  if( cmGrPageIsValid(pageHandle()) == false )
59
+    return;
60
+
61
+  // set the arrangement of 'views' on the 'page'
62
+  // (2 rows, 1 column)
63
+  initViews(kViewCnt,1);
64
+
65
+  unsigned   vwIdx = kAudioVwIdx;
66
+  cmGrPgH_t  grPgH = pageHandle();
67
+  cmGrVwH_t  grVwH = cmGrPageViewHandle( grPgH, vwIdx);
68
+  cmGrH_t    grH   = cmGrViewGrHandle( grVwH );
69
+  cmGrAxH_t  grAxH = cmGrAxNullHandle;
70
+  cmGrVExt_t limExt;
71
+
72
+  // register plot hash mark labelling functions
73
+  _samplesMetricId = cmGrPageLabelFuncRegister( grPgH, _s_roundHashValueFunc,    this, "Round" );              
74
+  _secondsMetricId = cmGrPageLabelFuncRegister( grPgH, _s_minSecMsHashValueFunc, this, "Min:Sec:Ms" );              
75
+  unsigned pitchLabelFuncId  = cmGrPageLabelFuncRegister( grPgH, _s_midiSciPitchValueFunc, this, "Pitch" );
76
+  //unsigned timeLabelFuncId =   _secondsMetricId;
77
+
78
+  
79
+  cmGrVExtSetD(&limExt,0,-1,0,1);
80
+  cmGrObjSetWorldLimitExt(grH, cmGrRootObjH(grH), &limExt, kTopGrFl | kBottomGrFl );
81
+
82
+  grAxH = cmGrViewAxisHandle(grVwH, kBottomGrIdx);
83
+  cmGrAxisSetCfg( grAxH, cmClrFlag(cmGrAxisCfg( grAxH ), kHashMarkGrFl | kHashLabelGrFl ));
84
+
85
+  //grAxH = cmGrViewAxisHandle(grVwH, kTopGrIdx );
86
+  //cmGrAxisSetLabelFunc(      grAxH, timeLabelFuncId );
87
+
88
+  grAxH = cmGrViewAxisHandle(grVwH, kRightGrIdx);
89
+  cmGrAxisSetCfg( grAxH, cmClrFlag(cmGrAxisCfg( grAxH ), kHashLabelGrFl ));
90
+
91
+  //cmGrViewSetLabelFunc(  grVwH, kTopGrIdx, timeLabelFuncId );
92
+  cmGrViewSetCfg( grVwH, cmSetFlag(cmGrViewCfg(grVwH),kSelectHorzGrFl)  );
93
+
94
+  vwIdx    = kMidiVwIdx;
95
+  grVwH    = cmGrPageViewHandle( grPgH, vwIdx);
96
+  grH      = cmGrViewGrHandle( grVwH );
97
+
98
+
99
+
100
+  cmGrVExtSetD(&limExt,0,0,0,127);
101
+  cmGrObjSetWorldLimitExt(grH, cmGrRootObjH(grH), &limExt, kTopGrFl | kBottomGrFl );
102
+
103
+  grAxH = cmGrViewAxisHandle(grVwH, kTopGrIdx);
104
+  cmGrAxisSetCfg(       grAxH, cmClrFlag(cmGrAxisCfg( grAxH ), kHashMarkGrFl | kHashLabelGrFl ));
105
+
106
+  //grAxH = cmGrViewAxisHandle(grVwH, kBottomGrIdx );
107
+  //cmGrAxisSetLabelFunc(      grAxH, timeLabelFuncId );
108
+
109
+  grAxH = cmGrViewAxisHandle(grVwH, kRightGrIdx);
110
+  cmGrAxisSetCfg( grAxH, cmClrFlag(cmGrAxisCfg( grAxH ), kHashLabelGrFl ));
111
+
112
+  grAxH = cmGrViewAxisHandle(grVwH, kLeftGrIdx );
113
+  cmGrAxisSetLabelFunc( grAxH, pitchLabelFuncId );
114
+
115
+  //cmGrViewSetLabelFunc(  grVwH, kTopGrIdx,  timeLabelFuncId );
116
+  cmGrViewSetLabelFunc(  grVwH, kLeftGrIdx, pitchLabelFuncId );
117
+  cmGrViewSetCfg( grVwH, cmSetFlag(cmGrViewCfg(grVwH),kSelectHorzGrFl)  );
118
+  
119
+  cmGrSetSync( grH, cmGrViewGrHandle( cmGrPageViewHandle( grPgH, kAudioVwIdx ) ), kWorldSyncGrFl | kViewSyncGrFl | kSelectSyncGrFl | kHorzSyncGrFl );
120
+  cmGrSetSync( cmGrViewGrHandle( cmGrPageViewHandle( grPgH, kAudioVwIdx ) ), grH, kWorldSyncGrFl | kViewSyncGrFl | kSelectSyncGrFl | kHorzSyncGrFl );  
121
+
122
+  setTimeAxisMetric(kSecondsMetricId);
123
+}
124
+
125
+cmGrTlFltk::~cmGrTlFltk()
126
+{
127
+  cmMemFree(_seqItemArray);
128
+}
129
+
130
+void cmGrTlFltk::_insertTimeLineObj( const cmTlUiMsg_t* m )
131
+{
132
+  cmGrPlH_t         plH         = plotHandle();
133
+  cmGrPgH_t         pgH         = pageHandle();
134
+
135
+  cmGrPlObjH_t      parentObjH  = cmGrPlObjNullHandle;
136
+  cmGrPlObjH_t      xAnchorObjH = cmGrPlObjNullHandle;
137
+  cmGrPlObjH_t      yAnchorObjH = cmGrPlObjNullHandle;
138
+  cmGrPlObjH_t      objH        = cmGrPlObjNullHandle;
139
+
140
+  const cmTlObj_t*  top         = _cmdIf->tlObjIdToPtr(m->objId);
141
+
142
+  assert(top != NULL);
143
+  if( top==NULL)
144
+    return;
145
+
146
+  unsigned               parentObjId = (top!=NULL && top->ref!=NULL) ? top->ref->uid : cmInvalidId;
147
+  const cmTlMidiEvt_t*   mep         = NULL;
148
+  const cmTlAudioFile_t* afp         = NULL;
149
+  unsigned               vwIdx       = kAudioVwIdx;
150
+  cmGrPlObjTypeId_t      objTypeId   = kRectGrPlId;
151
+  cmReal_t               x           = top->begSmpIdx;
152
+  cmReal_t               y           = -1.0;
153
+  cmReal_t               w           = top->durSmpCnt;
154
+  cmReal_t               h           = 2.0;
155
+  const cmChar_t*        label       = top->name;
156
+  unsigned               flags       = kNoDragGrPlFl;
157
+  bool                   pedalFl     = false;
158
+  cmGrVExt_t             wext;
159
+
160
+  cmGrVExtSetNull(&wext);
161
+
162
+  // convert cmTlUiMsg_t into parameters for a call to cmGrPlotObjCreate().
163
+  switch( top->typeId )
164
+  {
165
+    case kMidiFileTlId:  
166
+      {
167
+        vwIdx = kMidiVwIdx;
168
+        y     = 0;
169
+        h     = 127;
170
+        flags |= kNoFillGrPlFl | kNoSelectGrPlFl;
171
+
172
+        cmGrVExtSet(&wext,0,0,top->durSmpCnt,h);
173
+
174
+        if( parentObjId != cmInvalidId )
175
+          xAnchorObjH = cmGrPlotObjectIdToHandle( plH, parentObjId );
176
+
177
+        //printf("midi file id:%i x:%f y:%f w:%f h:%f %s\n",m->objId,x,y,w,h,cmStringNullGuard(label));
178
+      }
179
+      break;
180
+
181
+    case kMidiEvtTlId:
182
+      {
183
+        mep           = _cmdIf->tlMidiEvtObjPtr(top);
184
+        vwIdx         = kMidiVwIdx;
185
+        y             = 127; // all non-note-on msg's get put to the top of the display
186
+        h             = 1;
187
+        w             = 100; // arbitrary msg duration 
188
+
189
+        xAnchorObjH = cmGrPlotObjectIdToHandle( plH, parentObjId );
190
+        parentObjH  = cmGrPlotObjectIdToHandle( plH, mep->midiFileObjId );
191
+
192
+        assert( cmHandlesAreNotEqual(xAnchorObjH,cmGrPlObjNullHandle) );
193
+        assert( cmHandlesAreNotEqual(parentObjH,cmGrPlObjNullHandle) );
194
+
195
+        const cmMidiTrackMsg_t* mtm    = mep->msg;
196
+        cmMidiByte_t            status = mtm->status;
197
+
198
+        if( cmMidiIsNoteOn(status) )
199
+        {
200
+          y     = mtm->u.chMsgPtr->d0;
201
+          w     = top->durSmpCnt;
202
+          label = cmMidiToSciPitch(mtm->u.chMsgPtr->d0,NULL,0);
203
+        }
204
+        else
205
+        {
206
+          if( cmMidiIsSustainPedalDown(status,mtm->u.chMsgPtr->d0,mtm->u.chMsgPtr->d1) )
207
+          {
208
+            y      = 64;
209
+            w      = top->durSmpCnt;
210
+            flags += kNoFillGrPlFl;
211
+            label  = "Pedal";
212
+            pedalFl= true;
213
+          }
214
+          else
215
+          {
216
+            if( status == kMetaStId )
217
+              label = cmMidiMetaStatusToLabel(mtm->metaId);
218
+            else
219
+              label = cmMidiStatusToLabel(status);
220
+          }
221
+        }
222
+
223
+      }
224
+      break;
225
+
226
+    case kAudioFileTlId:
227
+      afp = _cmdIf->tlAudioFileObjPtr(top);
228
+      if( parentObjId != cmInvalidId )
229
+        xAnchorObjH = cmGrPlotObjectIdToHandle( plH, parentObjId );
230
+      cmGrVExtSet(&wext,0,-1,top->durSmpCnt,h);
231
+      //printf("audio file id:%i x:%f y:%f w:%f h:%f %s\n",m->objId,x,y,w,h,cmStringNullGuard(label));
232
+      break;
233
+
234
+    case kAudioEvtTlId:
235
+      objTypeId = kVLineGrPlId;
236
+      break;
237
+
238
+    case kMarkerTlId:
239
+      if( _cmdIf->tlMarkerObjPtr(top)->typeId == kMidiOnsetMarkTlId )
240
+        vwIdx = kMidiVwIdx;
241
+
242
+      objTypeId   = kVLineGrPlId;
243
+      xAnchorObjH = cmGrPlotObjectIdToHandle( plH, parentObjId );
244
+      //flags      |= kNoFillGrPlFl | kBorderSelGrPlFl | kNoFocusGrPlFl;
245
+      w = 0;
246
+      break;
247
+
248
+    default:
249
+      { assert(0); }
250
+  }
251
+
252
+  cmGrVwH_t vwH  = cmGrPageViewHandle(   pgH, vwIdx );
253
+  cmGrH_t   cvH  = cmGrViewGrHandle( vwH );
254
+  
255
+  //const cmChar_t* anchLabel   = cmHandlesAreEqual(xAnchorObjH,cmGrPlObjNullHandle) ? NULL : cmGrPlotObjLabel(xAnchorObjH);
256
+  //const cmChar_t* parentLabel = cmHandlesAreEqual(parentObjH,cmGrPlObjNullHandle)  ? NULL : cmGrPlotObjLabel(parentObjH);
257
+  //printf("type:%i id:%i x:%f y:%f w:%f h:%f %s  parent:%s xachor:%s\n",m->typeId,m->objId,x,y,w,h,cmStringNullGuard(label),cmStringNullGuard(parentLabel),cmStringNullGuard(anchLabel));
258
+
259
+  // Create the object
260
+  if( cmGrPlotObjCreate(plH, cvH, &objH, m->objId, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags, x, y, w, h, label, cmGrVExtIsNull(&wext)?NULL:&wext ) != kOkGrPlRC )
261
+  {
262
+    cmErrMsg(&_err,kInsertObjFailRC,"Insert failed on the object labelled '%s'.", cmStringNullGuard(top->name));
263
+    return;
264
+  }
265
+
266
+  // set the plot obj's user arg. to be the time line element pointer 
267
+  cmGrPlotObjSetUserPtr(objH,(void*)top);
268
+
269
+  // if the sequence is changing then invalidate the currently selected marker object
270
+  if( m->seqId != _curSeqId )
271
+  {
272
+    _curSeqId        = m->seqId;
273
+    _selMarkPlotObjH = cmGrPlObjNullHandle;
274
+  }
275
+
276
+  // Modify the objects attributes
277
+  if( cmGrPlotObjIsValid(objH) )
278
+  {
279
+    switch( top->typeId )
280
+    {
281
+      case kMidiEvtTlId:
282
+        cmGrPlotObjSetFontSize(objH,9);
283
+        
284
+        if( pedalFl )
285
+          cmGrPlotObjSetLineColor( objH, kEnablePlGrId, kGreenGrId );
286
+        else
287
+          cmGrPlotObjSetLineColor( objH, kEnablePlGrId, cmGrPlotObjFillColor(objH,kEnablePlGrId) );
288
+        
289
+        _setMidiEventLabels(objH,_getMenuCheckFlags());
290
+        break;
291
+      
292
+      case kAudioFileTlId:
293
+        if( afp->fn != NULL )
294
+          _cmdIf->audioFileLoad(afp->fn,m->objId);
295
+        break;
296
+
297
+      case kMarkerTlId:
298
+        {
299
+          cmGrColor_t   color = kBlackGrId;
300
+          const cmTlMarker_t* mop  = _cmdIf->tlMarkerObjPtr(top);
301
+          switch( mop->typeId)
302
+          {
303
+            case kAudioMarkTlId:
304
+              {
305
+                unsigned      n     = cmGrColorMapEleCount( cvH, kGrDefaultColorMapId );
306
+                unsigned      ci    = _markCnt++ % n;
307
+                color = cmGrColorMap(cvH,kGrDefaultColorMapId)[ci];
308
+              }
309
+              break;
310
+                
311
+            case kAudioOnsetMarkTlId:
312
+              color = kDarkRedGrId;
313
+              break;
314
+              
315
+            case kMidiOnsetMarkTlId:
316
+              color = kDarkBlueGrId;
317
+              break;
318
+
319
+            default:
320
+              { assert(0); }
321
+          }
322
+
323
+          cmGrPlotObjSetLabelAttr( objH, kNorthJsGrFl | kWestJsGrFl | kTopJsGrFl | kRightJsGrFl, 0, color );
324
+          cmGrPlotObjSetLineColor( objH, kEnablePlGrId, color );;
325
+          cmGrPlotObjSetPhysExt(objH, 1, 0, 1, 0 );
326
+
327
+          // create the marker end indicator
328
+          objH = cmGrPlObjNullHandle;
329
+          if( cmGrPlotObjCreate(plH, cvH, &objH, cmInvalidId, parentObjH, xAnchorObjH, yAnchorObjH, objTypeId, flags | kNoSelectGrPlFl, x+top->durSmpCnt, y, w, h, "", NULL ) != kOkGrPlRC )
330
+            cmErrMsg(&_err,kInsertObjFailRC,"Insert failed ending marker line labelled '%s'.", cmStringNullGuard(top->name));
331
+          else
332
+            cmGrPlotObjSetLineColor( objH, kEnablePlGrId, color );
333
+
334
+
335
+        }
336
+        break;
337
+
338
+      default:
339
+        break;
340
+    }
341
+  }
342
+}
343
+
344
+cmTlUiMsgTypeId_t cmGrTlFltk::recvTimeLineMsg( const void* msg, unsigned msgByteCnt )
345
+{
346
+  cmTlUiMsg_t m;
347
+
348
+  cmTimeLineDecode(msg,msgByteCnt,&m);
349
+  
350
+  switch( m.msgId )
351
+  {
352
+    case kInitMsgTlId:
353
+      {
354
+        // remove all objects from all views
355
+        cmGrPageClear(pageHandle());
356
+        _srate = m.srate;
357
+        _updateSeqMenu(m.seqCnt,m.seqId);
358
+      }
359
+      break;
360
+
361
+    case kDoneMsgTlId:
362
+      //size(w(),h()+1);
363
+      break;
364
+
365
+    case kFinalMsgTlId:      
366
+      break;
367
+
368
+    case kInsertMsgTlId:
369
+      _insertTimeLineObj(&m);
370
+      break;
371
+      
372
+    default:
373
+      { assert(0); }
374
+  }
375
+
376
+  return m.msgId;
377
+}
378
+
379
+void cmGrTlFltk::recvAudioFileLoad( unsigned fileId )
380
+{
381
+  cmGrPlH_t    plH    = plotHandle();
382
+  cmGrPlObjH_t grPlObjH = cmGrPlotObjectIdToHandle( plH, fileId );
383
+  cmAfmFileH_t afH      = _cmdIf->audioFileHandle( fileId );
384
+  unsigned     chIdx    = 0;
385
+
386
+  if( cmAfmFileIsValid(afH) == false )
387
+  {
388
+    cmErrMsg(&_err,kAudioObjFailRC,"Unable to locate audio file plot graphic object for id:%i.", fileId);  
389
+    return;
390
+  }
391
+
392
+  if(  cmGrPlotAudioFileObjCreate( grPlObjH, afH, chIdx ) != kOkGrPlRC )
393
+  {
394
+    const cmChar_t* audioFn = cmAudioFileName(cmAfmFileHandle(afH));
395
+    cmErrMsg(&_err,kAudioObjFailRC,"Create audio file graphic object failed for '%s'.", cmStringNullGuard(audioFn));
396
+    return;
397
+  }
398
+
399
+  redraw();
400
+}
401
+
402
+void cmGrTlFltk::setTimeAxisMetric( timeAxisMetricId_t metricId )
403
+{
404
+  unsigned timeLabelFuncId = cmInvalidId;
405
+
406
+  switch( metricId )
407
+  {
408
+    case kSamplesMetricId:  timeLabelFuncId = _samplesMetricId; break;
409
+    case kSecondsMetricId:  timeLabelFuncId = _secondsMetricId; break;
410
+    default:
411
+      { assert(0); }
412
+  }
413
+
414
+  cmGrPgH_t  pgH = pageHandle();
415
+  cmGrVwH_t  vwH = cmGrPageViewHandle( pgH, kAudioVwIdx);
416
+  cmGrAxH_t  axH = cmGrViewAxisHandle( vwH, kTopGrIdx);
417
+
418
+  cmGrViewSetLabelFunc(  vwH, kTopGrIdx,  timeLabelFuncId );
419
+  cmGrAxisSetLabelFunc(  axH,             timeLabelFuncId );
420
+
421
+  vwH = cmGrPageViewHandle( pgH, kMidiVwIdx);
422
+  axH = cmGrViewAxisHandle( vwH, kBottomGrIdx);
423
+  cmGrViewSetLabelFunc(  vwH, kBottomGrIdx,  timeLabelFuncId );
424
+  cmGrAxisSetLabelFunc(  axH,                timeLabelFuncId );
425
+}
426
+
427
+void cmGrTlFltk::toggleMarkerText()
428
+{
429
+  cmGrPlH_t plH = plotHandle();
430
+  unsigned n = cmGrPlotObjectCount(plH);
431
+  unsigned i;
432
+  for(i=0; i<n; ++i)
433
+  {
434
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
435
+    if( cmGrPlotObjIsValid(poH) )
436
+      cmGrPlotObjTogCfgFlags(poH,kNoLabelGrPlFl);    
437
+  }
438
+  redraw();
439
+}
440
+
441
+
442
+unsigned cmGrTlFltk::timeLineSelectedMarkerId() const
443
+{ 
444
+  const cmTlObj_t*    top;
445
+  
446
+  if( cmGrPlotObjIsValid(_selMarkPlotObjH) 
447
+    && cmIsFlag(cmGrPlotObjStateFlags(_selMarkPlotObjH),kSelectGrPlFl)
448
+    && (top = (const cmTlObj_t*)cmGrPlotObjUserPtr(_selMarkPlotObjH)) != NULL
449
+    && (top->typeId==kMarkerTlId || top->typeId==kMidiEvtTlId)   )
450
+    {
451
+      return top->uid;
452
+    }
453
+  return cmInvalidId;
454
+}
455
+
456
+void cmGrTlFltk::setAudioFileCursor( unsigned smpIdx )
457
+{
458
+  if( cmGrPlotObjIsValid(_selMarkPlotObjH) )
459
+  {
460
+    cmGrPlObjH_t poh;
461
+    // get the audio file plot object handle
462
+    if(cmGrPlotObjIsValid(poh = cmGrPlotObjXAnchor(_selMarkPlotObjH)))
463
+    {
464
+      cmGrVExt_t  vext;
465
+      cmGrVPt_t   pt0,pt1;
466
+
467
+      // get the canvas handle
468
+      cmGrPgH_t   pgH = pageHandle();
469
+      cmGrVwH_t   vwH = cmGrPageViewHandle(   pgH, kAudioVwIdx );
470
+      cmGrH_t     cvH = cmGrViewGrHandle( vwH );
471
+
472
+      cmGrPlotObjVExt(poh,&vext);  // get the extents of the audio file object
473
+      smpIdx += vext.loc.x;        // offset the current sample index to put the index in global time 
474
+
475
+      cmGrViewExtents(cvH, &vext );                 // get the current view extents
476
+      cmGrVPtSet(&pt0,smpIdx,cmGrVExtMinY(&vext));  // setup the selection points
477
+      cmGrVPtSet(&pt1,smpIdx,cmGrVExtMaxY(&vext));
478
+
479
+      cmGrSetSelectPoints(cvH, &pt0, &pt1 );        // apply the selection points to form a cursor line
480
+    }
481
+  }
482
+}
483
+
484
+void cmGrTlFltk::selectBar( unsigned barNumb )
485
+{
486
+  cmGrPlH_t    plH = plotHandle();
487
+  unsigned     n = cmGrPlotObjectCount(plH);
488
+  unsigned     i;
489
+  
490
+  for(i=0; i<n; ++i)
491
+  {
492
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
493
+    const cmTlMarker_t* mkp;
494
+    const cmTlObj_t*    top;
495
+
496
+    if( cmGrPlotObjIsValid(poH)
497
+      && (top = (const cmTlObj_t*)cmGrPlotObjUserPtr(poH)) != NULL
498
+      && top->typeId == kMarkerTlId 
499
+      && (mkp = _cmdIf->tlMarkerObjPtr(top)) != NULL
500
+      && mkp->bar == barNumb ) // <-------- there is an apparent weakness in selecting a marker based 
501
+    {                          //           only on the bar number - because the intention is to pick a
502
+                               //           bar line marker but it may be (i have not actually checked)
503
+                               //           that other objects might have a given bar number but not be
504
+                               //           a bar line object.
505
+
506
+      unsigned flags = cmGrPlotObjStateFlags(poH);
507
+      
508
+      cmGrPlotObjSetStateFlags(poH,cmSetFlag(flags,kFocusGrPlFl | kSelectGrPlFl));
509
+      redraw();
510
+      
511
+      _selMarkPlotObjH = poH;
512
+
513
+      _cmdIf->onTimeLineMarkerSelected(mkp->obj.uid);
514
+      
515
+    }
516
+  }
517
+  
518
+}
519
+
520
+bool cmGrTlFltk::on_plot_object(   cmGrPlotCbArg_t* arg )
521
+{
522
+  if( arg->selId==kStateChangeGrPlId 
523
+    &&  cmIsFlag(arg->deltaFlags,kSelectGrPlFl) 
524
+    &&  cmIsFlag(cmGrPlotObjStateFlags(arg->objH),kSelectGrPlFl) )
525
+  {
526
+    const cmTlObj_t* top;
527
+    if((top = (const cmTlObj_t*)cmGrPlotObjUserPtr(arg->objH)) != NULL)
528
+    {
529
+      const cmChar_t* s = NULL;
530
+
531
+      switch(top->typeId)
532
+      {
533
+        case kAudioFileTlId:
534
+          {
535
+            const cmTlAudioFile_t*  afp;
536
+            if((afp = _cmdIf->tlAudioFileObjPtr(top)) != NULL && afp->fn != NULL)
537
+              s = afp->fn;
538
+          }
539
+          break;
540
+
541
+        case kMidiFileTlId:
542
+          {
543
+            const cmTlMidiFile_t*  mfp;
544
+            if((mfp = _cmdIf->tlMidiFileObjPtr(top)) != NULL && mfp->fn != NULL)
545
+              s = mfp->fn;
546
+          }
547
+          break;
548
+
549
+        case kMidiEvtTlId:
550
+          {
551
+            const cmTlMidiEvt_t* mep;
552
+            if((mep = _cmdIf->tlMidiEvtObjPtr(top)) != NULL )
553
+            {
554
+              _selMarkPlotObjH = arg->objH;
555
+
556
+              callback()(this,user_data());
557
+              
558
+              _cmdIf->onTimeLineMidiEvtSelected(mep->obj.uid);
559
+            }
560
+          }
561
+          break;
562
+
563
+        case kMarkerTlId:
564
+          {
565
+            const cmTlMarker_t*  mkp;
566
+            if((mkp = _cmdIf->tlMarkerObjPtr(top)) != NULL)
567
+            {
568
+              if(mkp->text != NULL)
569
+                s = mkp->text;
570
+
571
+              _selMarkPlotObjH = arg->objH;
572
+
573
+              callback()(this,user_data());
574
+
575
+              _cmdIf->onTimeLineMarkerSelected(mkp->obj.uid);
576
+
577
+            }
578
+          }
579
+          break;
580
+
581
+        default:
582
+          break;
583
+      }
584
+    
585
+      if( s == NULL )
586
+        s = cmGrPlotObjLabel(arg->objH);
587
+
588
+      if( s == NULL )
589
+        s = "";
590
+
591
+      setStatusText(s);
592
+    }
593
+  }
594
+
595
+  return true;
596
+}
597
+
598
+
599
+
600
+void cmGrTlFltk::_s_seqMenuCallback( Fl_Widget* w, void* vp )
601
+{
602
+  item_t* ip = (item_t*)vp;
603
+  assert( ip->id < ip->p->_seqCnt );
604
+  ip->p->_cmdIf->selectSequence(ip->id);
605
+}
606
+
607
+void cmGrTlFltk::_s_roundHashValueFunc(   void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
608
+{
609
+  snprintf(label,labelCharCnt,"%i",(int)round(value));
610
+}
611
+
612
+void cmGrTlFltk::_s_minSecMsHashValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
613
+{
614
+  cmGrTlFltk* p = (cmGrTlFltk*)arg;
615
+  
616
+  int min=0,sec=0,ms=0;
617
+
618
+  double smpPerMin = p->_srate * 60.0;
619
+  double smpPerMs  = p->_srate / 1000.0;
620
+
621
+  if( value > smpPerMin ) 
622
+  {
623
+    min    = (int)floor( value / smpPerMin );
624
+    value -= min * smpPerMin;
625
+  }
626
+
627
+  if( value > p->_srate )
628
+  {
629
+    sec    = (int)floor( value / p->_srate );
630
+    value -= sec * p->_srate;
631
+  }
632
+
633
+
634
+  if( value > smpPerMs )
635
+  {
636
+    ms     = (int)floor( value / smpPerMs );
637
+    value -= ms * smpPerMs;
638
+  }
639
+
640
+  snprintf(label,labelCharCnt,"%i:%2i:%2i",min,sec,ms); 
641
+}
642
+
643
+void cmGrTlFltk::_s_midiSciPitchValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
644
+{
645
+  assert( label != NULL && labelCharCnt > 0 );
646
+
647
+  if( labelCharCnt > 0 )
648
+    label[0] = 0;
649
+
650
+  if( 0 <= value && value <= 127 )
651
+    cmMidiToSciPitch((cmMidiByte_t)floor(value), label, labelCharCnt );
652
+  else
653
+  {
654
+    if( labelCharCnt > 3 )
655
+      strcpy(label,"?");
656
+  }
657
+}
658
+
659
+void cmGrTlFltk::_updateSeqMenu(int newSeqCnt, unsigned seqId)
660
+{
661
+  if(_seqMenuIdx == -1 )
662
+    return;
663
+
664
+  //const Fl_Menu_Item* seq_mip = _menuBar->menu() + _seqMenuIdx;
665
+  //int sz = seq_mip->size();
666
+
667
+  // if the count of time-line sequences does not match the new count of sequences
668
+  if( 1 /*sz != newSeqCnt*/ )
669
+  {
670
+    int i;
671
+    // erase the current sequence sub-menu
672
+    _menuBar->clear_submenu(_seqMenuIdx);
673
+
674
+    // create an array to link the menu items to the sequence control id's
675
+    _seqItemArray = cmMemResizeZ(item_t,_seqItemArray,newSeqCnt);
676
+
677
+    // create each menu items and item map record
678
+    for(i=0; i<newSeqCnt; ++i)
679
+    {
680
+      _seqItemArray[i].id = i;
681
+      _seqItemArray[i].p = this;
682
+      _menuBar->insert(_seqMenuIdx + i + 1,cmTsPrintf("%i",i),0,_s_seqMenuCallback,_seqItemArray+i,FL_MENU_TOGGLE);            
683
+    }
684
+
685
+  }
686
+
687
+  // set the menu check boxes to indicate the selected sequence
688
+  int i;
689
+  for(i=0; i<newSeqCnt; ++i)
690
+  {
691
+    Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + _seqMenuIdx + i + 1;
692
+    if( i == (int)seqId )
693
+      mip->set();
694
+    else
695
+      mip->clear();
696
+  }      
697
+
698
+  // track the current sequence count
699
+  _seqCnt = newSeqCnt;
700
+  
701
+}
702
+
703
+void cmGrTlFltk::_createMenu( )
704
+{
705
+  _seqMenuIdx = _menuBar->add("Seq",      0,NULL,0,FL_SUBMENU);
706
+  int idx     = _menuBar->add("Time Line",0,NULL,0,FL_SUBMENU);
707
+  const char* titleArray[] = { "Samples", "Seconds", "Marker Text", "Pitch", "Velocity","Id",   "Gen Onset","Del Onset" };
708
+  bool        checkFl[]    = { false,     false,     false,          true,   true,       true,   false,     false };
709
+  bool        onFl[]       = { false,     false,     false,          true,   false,      false,  false,     false };
710
+  int i;
711
+  for(i=0; i<kMenuItemCnt; ++i)
712
+  {
713
+    int flag = checkFl[i] ? FL_MENU_TOGGLE : 0;
714
+    _menuArray[i].id = i;
715
+    _menuArray[i].p  = this;
716
+    _menuBar->insert(idx+1+i,titleArray[i],0,_s_menuCallback, _menuArray + i, flag );
717
+
718
+    if( onFl[i] )
719
+    {
720
+      Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + idx + i + 1;
721
+      mip->set();
722
+    }   
723
+  }
724
+}
725
+
726
+bool cmGrTlFltk::_isMenuChecked( int id )
727
+{
728
+  unsigned i;
729
+  // locate the menu item assoc'd with id
730
+  for(i=0; i<kMenuItemCnt; ++i)
731
+    if( _menuArray[i].id == id )
732
+      break;
733
+
734
+  assert( i < kMenuItemCnt );
735
+
736
+  int menuIdx;
737
+  if(( menuIdx = _menuBar->find_index("Time Line")) == -1 )
738
+    return false;
739
+  
740
+  // The menu items and _menuArray[] were initialized in the same order
741
+  // therefore the offset from the base of both should be the same.
742
+  Fl_Menu_Item* mip = (Fl_Menu_Item*)_menuBar->menu() + menuIdx + i + 1;
743
+
744
+  assert( (item_t*)mip->user_data() == _menuArray + i );
745
+
746
+  return mip->value() != 0;
747
+}
748
+
749
+unsigned cmGrTlFltk::_getMenuCheckFlags()
750
+{
751
+  unsigned  flags = 0;
752
+  flags |= _isMenuChecked(kViewPitchMId)      ? kPitchChkFl : 0;
753
+  flags |= _isMenuChecked(kViewVelocityMId)   ? kVelChkFl   : 0;
754
+  flags |= _isMenuChecked(kViewIdMId)         ? kIdChkFl    : 0;
755
+  return flags;
756
+}
757
+
758
+void cmGrTlFltk::_setLabels()
759
+{
760
+  cmGrPlH_t plH   = plotHandle();
761
+  unsigned  flags = _getMenuCheckFlags();
762
+  unsigned  n     = cmGrPlotObjectCount(plH);
763
+  unsigned  i;
764
+  for(i=0; i<n; ++i)
765
+  {
766
+    cmGrPlObjH_t poH = cmGrPlotObjectIndexToHandle(plH,i);
767
+    _setMidiEventLabels(poH,flags);
768
+  }
769
+}
770
+
771
+void cmGrTlFltk::_setMidiEventLabels( cmGrPlObjH_t poH, unsigned flags)
772
+{
773
+  cmTlObj_t*   top;
774
+  if( cmGrPlotObjIsValid(poH) && (top = (cmTlObj_t*)cmGrPlotObjUserPtr(poH))!=NULL && top->typeId==kMidiEvtTlId )
775
+  {
776
+    const cmMidiTrackMsg_t* mep = ((const cmTlMidiEvt_t*)top)->msg;
777
+    if( mep->status == kNoteOnMdId )
778
+    {
779
+      int      bufN = 255;
780
+      cmChar_t buf[ bufN+1 ];
781
+
782
+      buf[bufN] = 0;
783
+      buf[0]    = 0;
784
+
785
+      if( cmIsFlag(flags,kPitchChkFl) )
786
+        snprintf(buf+strlen(buf),bufN-strlen(buf),"%s ",cmMidiToSciPitch(mep->u.chMsgPtr->d0,NULL,0));      
787
+
788
+      if( cmIsFlag(flags,kVelChkFl) )
789
+        snprintf(buf+strlen(buf),bufN-strlen(buf),"%i ",mep->u.chMsgPtr->d1);
790
+
791
+      if( cmIsFlag(flags,kIdChkFl) )
792
+        snprintf(buf+strlen(buf),bufN-strlen(buf),"%i ",mep->uid);
793
+
794
+      cmGrPlotObjSetLabel(poH, buf );
795
+    }
796
+  }
797
+}
798
+
799
+void cmGrTlFltk::_s_menuCallback(Fl_Widget* w, void* arg )
800
+{
801
+  item_t*          ip = (item_t*)arg;
802
+  cmGrTlFltk*  p  = ip->p;
803
+  unsigned long    id = ip->id;
804
+
805
+  switch( id )
806
+  {
807
+    case kViewSamplesMId:
808
+    case kViewSecondsMId:
809
+      {
810
+        cmGrTlFltk::timeAxisMetricId_t  metricId = id==kViewSamplesMId ? cmGrTlFltk::kSamplesMetricId : cmGrTlFltk::kSecondsMetricId;
811
+        p->setTimeAxisMetric( metricId );
812
+        p->redraw();
813
+      }
814
+      break;
815
+
816
+    case kViewMarkTextMId:
817
+      p->toggleMarkerText();
818
+      break;
819
+
820
+    case kViewVelocityMId:
821
+    case kViewPitchMId:
822
+    case kViewIdMId:
823
+      p->_setLabels();
824
+      p->redraw();
825
+      break;
826
+
827
+    case kGenOnsetMarksMId:
828
+      p->_cmdIf->generateOnsetMarks();
829
+      break;
830
+
831
+    case kDelOnsetMarksMId:
832
+      p->_cmdIf->deleteOnsetMarks();
833
+      break;
834
+  }
835
+}

+ 108
- 0
src/tlCtl/cmGrTlFltk.h View File

@@ -0,0 +1,108 @@
1
+#ifndef cmGrTlFltk_h
2
+#define cmGrTlFltk_h
3
+
4
+class Fl_Menu_Bar;
5
+class cmdIf;
6
+
7
+
8
+class cmGrTlFltk : public cmGrPlotFltk, public gvHashFuncArg
9
+{
10
+ public:
11
+  cmGrTlFltk(cmCtx_t* ctx, cmdIf* cp, Fl_Menu_Bar* menuBar, int x, int y, int w, int h);
12
+  virtual ~cmGrTlFltk();
13
+
14
+  virtual cmTlUiMsgTypeId_t recvTimeLineMsg( const void* msg, unsigned msgByteCnt );
15
+  virtual void              recvAudioFileLoad( unsigned fileId );
16
+
17
+  virtual double   sampleRate() const { return _srate; }
18
+
19
+  // Call these functions to notify the UI of changes of state that
20
+  // occurred programmatically.  These notifications are bubbling up
21
+  // from the engine.
22
+  typedef enum { kSamplesMetricId, kSecondsMetricId } timeAxisMetricId_t;
23
+  virtual void     setTimeAxisMetric( timeAxisMetricId_t metricId );
24
+  virtual void     toggleMarkerText();
25
+  virtual unsigned timeLineSelectedMarkerId() const;
26
+  virtual void     setAudioFileCursor( unsigned smpIdx );
27
+  virtual void     selectBar( unsigned barNumb );
28
+
29
+  // This function is called to notify the timeline UI that that state of one of it's
30
+  // UI elements has been changed/manipulated by the user.  This is the first
31
+  // point of contact with a requested change from the user which is being
32
+  // directed down to the engine.
33
+  virtual bool on_plot_object(   cmGrPlotCbArg_t* arg );
34
+
35
+ private:
36
+  enum
37
+  {
38
+    kOkRC,
39
+    kParentObjNotFoundRC,
40
+    kInsertObjFailRC,
41
+    kAudioObjFailRC,
42
+  };
43
+
44
+  enum
45
+  {
46
+    kAudioVwIdx,
47
+    kMidiVwIdx,
48
+    kViewCnt
49
+  };
50
+
51
+  enum
52
+  {
53
+    kViewSamplesMId,
54
+    kViewSecondsMId,
55
+    kViewMarkTextMId,
56
+    kViewPitchMId,
57
+    kViewVelocityMId,
58
+    kViewIdMId,
59
+    kGenOnsetMarksMId,
60
+    kDelOnsetMarksMId,
61
+    kMenuItemCnt
62
+  };
63
+
64
+  // Flags returned by _getMenuCheckFlags();
65
+  enum { kPitchChkFl=0x01, kVelChkFl=0x02, kIdChkFl=0x04 };
66
+
67
+
68
+  typedef struct item_str
69
+  {
70
+    cmGrTlFltk* p;
71
+    int         id;
72
+  } item_t;
73
+
74
+
75
+  cmErr_t      _err;
76
+  double       _srate;
77
+  cmdIf*       _cmdIf;
78
+  Fl_Menu_Bar* _menuBar;
79
+  int          _seqMenuIdx;
80
+  int          _seqCnt;
81
+  item_t*      _seqItemArray;
82
+  int          _markCnt;
83
+  unsigned     _samplesMetricId;
84
+  unsigned     _secondsMetricId;
85
+  cmGrPlObjH_t _selMarkPlotObjH;
86
+  unsigned     _curSeqId;
87
+  item_t       _menuArray[ kMenuItemCnt ];
88
+  
89
+
90
+  void     _insertTimeLineObj( const cmTlUiMsg_t* m );
91
+  void     _updateSeqMenu(int  newSeqCnt, unsigned seqId);
92
+  void     _createMenu();
93
+  bool     _isMenuChecked(int id);
94
+  unsigned _getMenuCheckFlags();
95
+  void     _setLabels();
96
+  void     _setMidiEventLabels( cmGrPlObjH_t poH, unsigned flags);
97
+
98
+  static void _s_seqMenuCallback( Fl_Widget* w, void* vp );
99
+
100
+  static void _s_midiSciPitchValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
101
+  static void _s_roundHashValueFunc(    void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
102
+  static void _s_minSecMsHashValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
103
+  static void _s_menuCallback( Fl_Widget* w, void* arg );
104
+};
105
+
106
+
107
+
108
+#endif

+ 650
- 0
src/tlCtl/cmdIf.cpp View File

@@ -0,0 +1,650 @@
1
+#include <FL/Fl.H>
2
+#include <FL/fl_draw.h>
3
+#include <FL/Fl_Widget.H>
4
+#include <FL/Fl_Double_Window.H>
5
+#include <Fl/Fl_Output.H>
6
+
7
+#include "cmPrefix.h"
8
+#include "cmGlobal.h"
9
+#include "cmFloatTypes.h"
10
+#include "cmRpt.h"
11
+#include "cmErr.h"
12
+#include "cmCtx.h"
13
+#include "cmMem.h"
14
+#include "cmMallocDebug.h"
15
+#include "cmLinkedHeap.h"
16
+#include "cmThread.h"
17
+#include "cmText.h"
18
+#include "cmFileSys.h"
19
+#include "cmJson.h"
20
+#include "cmPrefs.h"
21
+#include "cmSymTbl.h"
22
+#include "cmTime.h"
23
+#include "cmMidi.h"
24
+#include "cmMidiFile.h"
25
+#include "cmAudioFile.h"
26
+#include "cmTimeLine.h"
27
+
28
+#include "cmScore.h"
29
+
30
+#include "cmProcObj.h"
31
+#include "cmProc4.h"
32
+
33
+#include "cmAudioFileMgr.h"
34
+#include "cmdIf.h"
35
+
36
+#include <sstream>
37
+
38
+
39
+//-------------------------------------------------------------------------------------
40
+//-------------------------------------------------------------------------------------
41
+//-------------------------------------------------------------------------------------
42
+
43
+cmdIf::cmdIf( cmCtx_t* ctx, cmdIfRspdr* rspdr, const cmChar_t* audioPath )
44
+  : _ctx(ctx),_thH(cmThreadNullHandle),
45
+  _cmdQueH(cmTs1p1cNullHandle),_outQueH(cmTs1p1cNullHandle),
46
+  _tlH(cmTimeLineNullHandle),_afmH(cmAfmNullHandle),_scH(cmScNullHandle),
47
+  _afPath(NULL),_rspdr(rspdr),_curSeqId(cmInvalidId)
48
+{
49
+  cmErrSetup(&_err,&ctx->rpt,"cmdIf");
50
+
51
+  cmAfmCreate(ctx,&_afmH);
52
+
53
+  cmThreadCreate( &_thH, _thFunc, this, &ctx->rpt );
54
+  cmTs1p1cCreate( &_cmdQueH, 4*64536, NULL, NULL, &_ctx->rpt );
55
+  cmTs1p1cCreate( &_outQueH, 4*64536, NULL, NULL, &_ctx->rpt );
56
+
57
+  if( audioPath != NULL )
58
+    setAudioFilePath(audioPath);
59
+}
60
+
61
+cmdIf::~cmdIf()
62
+{
63
+  cmThreadDestroy( &_thH );     // stop the thread to prevent interfering with que release
64
+  _releaseQue(&_cmdQueH);
65
+  _releaseQue(&_outQueH);
66
+  cmTimeLineFinalize(&_tlH);
67
+  cmAfmDestroy(&_afmH);
68
+  cmScoreFinalize(&_scH);
69
+  cmMemFree(_afPath);
70
+}
71
+
72
+cmdIf::rc_t cmdIf::open( const cmChar_t* fn )
73
+{  return _sendCmd(kOpenCmdId,0,fn); }
74
+
75
+cmdIf::rc_t cmdIf::close( )
76
+{  return _sendCmd(kCloseCmdId); }
77
+
78
+const cmChar_t* cmdIf::tlFileName() const
79
+{
80
+  if( cmTimeLineIsValid(_tlH) == false )
81
+    return NULL;
82
+
83
+  return cmTimeLineFileName(_tlH);
84
+}
85
+
86
+const cmTlMidiFile_t*  cmdIf::tlMidiFileObjPtr(  const cmTlObj_t* op ) const
87
+{ return cmTimeLineMidiFileObjPtr(_tlH,const_cast<cmTlObj_t*>(op)); }
88
+
89
+const cmTlAudioFile_t* cmdIf::tlAudioFileObjPtr( const cmTlObj_t* op ) const
90
+{ return cmTimeLineAudioFileObjPtr(_tlH,const_cast<cmTlObj_t*>(op)); }
91
+
92
+const cmTlMidiEvt_t*   cmdIf::tlMidiEvtObjPtr(   const cmTlObj_t* op ) const
93
+
94
+{ return cmTimeLineMidiEvtObjPtr(_tlH,const_cast<cmTlObj_t*>(op)); }
95
+
96
+const cmTlAudioEvt_t*  cmdIf::tlAudioEvtObjPtr(  const cmTlObj_t* op ) const
97
+{ return cmTimeLineAudioEvtObjPtr(_tlH,const_cast<cmTlObj_t*>(op)); }
98
+
99
+const cmTlMarker_t*    cmdIf::tlMarkerObjPtr(    const cmTlObj_t* op ) const
100
+{ return cmTimeLineMarkerObjPtr(_tlH,const_cast<cmTlObj_t*>(op)); }
101
+
102
+
103
+const cmChar_t* cmdIf::scoreFileName() const
104
+{
105
+  if( cmScoreIsValid(_scH) == false )
106
+    return NULL;
107
+  return cmScoreFileName(_scH);
108
+}
109
+
110
+const cmScoreEvt_t* cmdIf::scoreEventIdToPtr( unsigned scEvtId ) const
111
+{
112
+  if( cmScoreIsValid(_scH)==false )
113
+    return NULL;
114
+  return cmScoreEvt(_scH,scEvtId);
115
+}
116
+
117
+const cmScoreSection_t* cmdIf::scoreSectionIdToPtr( unsigned scSectId ) const
118
+{
119
+  if( cmScoreIsValid(_scH)==false)
120
+    return NULL;
121
+  return cmScoreSection(_scH,scSectId);
122
+}
123
+
124
+
125
+
126
+const cmTlObj_t* cmdIf::tlObjIdToPtr( unsigned tlObjId ) const
127
+{ return cmTlIdToObjPtr( _tlH, tlObjId ); }
128
+
129
+
130
+cmdIf::rc_t cmdIf::selectSequence( unsigned id )
131
+{ return _sendCmd(kSelectSeqCmdId,id); }
132
+
133
+
134
+cmdIf::rc_t cmdIf::audioFileLoad( const cmChar_t* fn, unsigned appFileId )
135
+{
136
+  const cmChar_t*      afFn = fn;
137
+  //cmFileSysPathPart_t* pp = NULL ;
138
+
139
+  /*
140
+  if( _afPath != NULL )
141
+  {
142
+    pp   = cmFsPathParts(fn);
143
+    afFn = cmFsMakeFn(_afPath,pp->fnStr,pp->extStr,NULL);
144
+  }
145
+  */
146
+
147
+  rc_t rc = _sendCmd(kAfLoadCmdId,appFileId,afFn);
148
+
149
+  /*
150
+  if( _afPath != NULL )
151
+  {
152
+    cmFsFreeFn(afFn);
153
+    cmFsFreePathParts(pp);
154
+  }
155
+  */
156
+    
157
+  return rc;
158
+}
159
+
160
+cmAfmFileH_t cmdIf::audioFileHandle( unsigned appFileId )
161
+{ return cmAfmIdToHandle(_afmH,appFileId); }
162
+
163
+void cmdIf::setAudioFilePath( const cmChar_t* path )
164
+{ _afPath = cmMemResizeStr(_afPath,path);  }
165
+
166
+cmdIf::rc_t cmdIf::setScore( const cmChar_t* scoreFn )
167
+{ return _sendCmd(kScoreCmdId,0,scoreFn); }
168
+
169
+void cmdIf::setScoreLocation( unsigned locIdx, unsigned smpIdx, unsigned pitch, unsigned vel )
170
+{ 
171
+ cmScoreSetPerfEvent(_scH,locIdx,smpIdx,pitch,vel); 
172
+}
173
+
174
+void cmdIf::setScoreVarValue( unsigned locIdx, unsigned varId, double value )
175
+{
176
+  cmScoreSetPerfValue(_scH,locIdx,varId,value);
177
+}
178
+
179
+void cmdIf::setScoreDynLevel( unsigned evtIdx, unsigned dynLvl )
180
+{
181
+  cmScoreSetPerfDynLevel(_scH,evtIdx,dynLvl);
182
+}
183
+
184
+
185
+void cmdIf::onTimeLineMarkerSelected( unsigned markerTlId )
186
+{
187
+  if( _rspdr != NULL )
188
+    _rspdr->cmdIfOnTimeLineMarkerSelect(markerTlId);
189
+
190
+  _onTimeLineObjSelected(markerTlId);
191
+
192
+}
193
+
194
+void cmdIf::onTimeLineMidiEvtSelected( unsigned midiEvtTlId )
195
+{
196
+  if( _rspdr != NULL )
197
+    _rspdr->cmdIfOnTimeLineMidiEvtSelect(midiEvtTlId);
198
+
199
+  _onTimeLineObjSelected(midiEvtTlId);  
200
+}
201
+
202
+void cmdIf::onScoreBarSelected( unsigned scoreIdx )
203
+{
204
+  if( cmScoreIsValid(_scH) )
205
+    cmScoreClearPerfInfo(_scH);
206
+
207
+  if( _rspdr != NULL )
208
+   _rspdr->cmdIfOnScoreBarSelect(scoreIdx);
209
+
210
+}
211
+
212
+cmdIf::rc_t   cmdIf::generateOnsetMarks()
213
+{ return _sendCmd( kGenOnsetMarksCmdId); }
214
+
215
+cmdIf::rc_t   cmdIf::deleteOnsetMarks()
216
+{ return _sendCmd( kDelOnsetMarksCmdId);  }
217
+
218
+
219
+bool cmdIf::isBusy() const
220
+{  return cmThreadIsValid(_thH) && cmThreadState(_thH)==kRunningThId;  }
221
+
222
+void cmdIf::onIdle()
223
+{
224
+  if( !cmTs1p1cIsValid(_outQueH) )
225
+    return;
226
+
227
+  // pick up msg's sent from the worker thread 
228
+  while( cmTs1p1cMsgWaiting(_outQueH) )
229
+  {
230
+    cmd_t    c;
231
+    cmThRC_t thRC;
232
+
233
+    if((thRC = cmTs1p1cDequeueMsg(_outQueH,&c,sizeof(c))) != kOkThRC )
234
+    {
235
+      _thErrorMsg("Deque response failed.");
236
+      continue;
237
+    }
238
+
239
+    //printf("deq th->app id:%i val:%i n:%i msg:%p\n",c.id,c.value,c.byteCnt,c.u.msg);
240
+
241
+    switch( c.id )
242
+    {
243
+      // the worker thread is busy - show a modal progress window
244
+      case kShowStatusCmdId:
245
+        _rspdr->cmdIfShowStatusMsg(c.u.string);
246
+        break;
247
+
248
+        // the worker thread is idle - remove the modal progress window
249
+      case kHideStatusCmdId:        
250
+        _rspdr->cmdIfHideStatus();
251
+        break;
252
+
253
+        // report an error which occured during a worker thread operation
254
+      case kErrMsgCmdId:
255
+        _rspdr->cmdIfErrorMsg(c.u.string);
256
+        break;
257
+
258
+        // send a msg to the time-line UI
259
+      case kTimeLineMsgCmdId:
260
+        _rspdr->cmdIfTimeLineMsg(c.u.msg,c.byteCnt);
261
+        break;
262
+
263
+      case kAfLoadCmdId:
264
+        _rspdr->cmdIfAudioFileLoad(c.value);
265
+        break;
266
+
267
+      case kScoreMsgCmdId:
268
+        _rspdr->cmdIfScoreMsg(c.u.msg,c.byteCnt);
269
+        break;
270
+
271
+      default:
272
+        break;
273
+    }
274
+
275
+    if( c.byteCnt )
276
+    {
277
+      cmMemFree(c.u.msg);
278
+    }
279
+  }
280
+}
281
+
282
+//----------------------------------------------------------------------------------------
283
+// App Thread Functions
284
+//----------------------------------------------------------------------------------------
285
+
286
+cmdIf::rc_t cmdIf::_sendCmd( cmdId_t id, unsigned value, const char* str )
287
+{ 
288
+  rc_t rc;
289
+  if((rc = _enqueue( _cmdQueH, id, value, str, str==NULL ? 0 : strlen(str)+1 )) == kOkRC )
290
+     cmThreadPause(_thH, 0 );
291
+  else
292
+  {
293
+    cmErrMsg(&_err,kCmdEnqueueFailRC,"Command enque failed.");
294
+  }
295
+
296
+  return rc;
297
+}
298
+
299
+void cmdIf::_releaseQue( cmTs1p1cH_t* queHPtr )
300
+{
301
+  
302
+  while( cmTs1p1cMsgWaiting(*queHPtr) )
303
+  {
304
+    cmd_t    c;
305
+    cmThRC_t thRC;
306
+
307
+    if((thRC = cmTs1p1cDequeueMsg(*queHPtr,&c,sizeof(c))) != kOkThRC )
308
+    {
309
+      // TODO: PRINT ERROR MSG HERE USING APP THREAD ERROR HANDLER
310
+      //_thErrorMsg("Deque command failed during queue draining.");
311
+      continue;
312
+    }
313
+
314
+
315
+    if( c.byteCnt )
316
+      cmMemFree(c.u.msg);
317
+    
318
+  }
319
+
320
+  cmTs1p1cDestroy(queHPtr);
321
+
322
+}
323
+
324
+//----------------------------------------------------------------------------------------
325
+// Worker Thread Functions
326
+//----------------------------------------------------------------------------------------
327
+bool cmdIf::_thFunc( void* arg )
328
+{
329
+  cmdIf* p = (cmdIf*)arg;
330
+
331
+  while( cmTs1p1cMsgWaiting(p->_cmdQueH) )
332
+  {
333
+    cmd_t    c;
334
+    cmThRC_t thRC;
335
+
336
+    if((thRC = cmTs1p1cDequeueMsg(p->_cmdQueH,&c,sizeof(c))) != kOkThRC )
337
+    {
338
+      p->_thErrorMsg("Deque command failed.");
339
+      continue;
340
+    }
341
+
342
+    switch(c.id )
343
+    {
344
+      case kOpenCmdId:
345
+        p->_thDoOpen(&c);
346
+        break;
347
+
348
+      case kCloseCmdId:
349
+        p->_thDoClose(&c);
350
+        break;
351
+
352
+      case kSelectSeqCmdId:
353
+        p->_thDoSelectSeq(&c);
354
+        break;
355
+
356
+      case kAfLoadCmdId:
357
+        p->_thDoAfLoad(&c);
358
+        break;
359
+
360
+      case kScoreCmdId:
361
+        p->_thDoScore(&c);
362
+        break;
363
+
364
+      case kGenOnsetMarksCmdId:
365
+        p->_thDoGenOnsetMarks(&c);
366
+        break;
367
+
368
+      case kDelOnsetMarksCmdId:
369
+        p->_thDoDelOnsetMarks(&c);
370
+        break;
371
+
372
+      default:
373
+        break;
374
+    }
375
+
376
+    if( c.byteCnt )
377
+      cmMemFree(c.u.msg);
378
+
379
+  }
380
+
381
+
382
+  cmThreadPause( p->_thH, kPauseThFl );
383
+
384
+  return true;
385
+}
386
+
387
+//void cmdIfRptFunc( void* user, const cmChar_t* text )
388
+//{ printf("%s",text); }
389
+
390
+void cmdIf::_thDoOpen(  const cmd_t* cmd )
391
+{
392
+  _thStatusMsg("Loading: '%s'",cmd->u.string);
393
+
394
+  if( cmTimeLineInitializeFromFile(_ctx,&_tlH,_thSendTimeLineMsg,this,cmd->u.string,_afPath) != kOkTlRC )
395
+    _thErrorMsg("Load failed on '%s'.",cmd->u.string);
396
+  else
397
+  {
398
+    _curSeqId = 0;
399
+
400
+    // Make notification callbacks for all time line records to _thSendTimeLineMsg()
401
+    // _thSendTimeLineMsg() then enqueues msg's into _outQueH which are picked
402
+    // up by the idle handler
403
+    cmTimeLineSeqNotify(_tlH,_curSeqId);
404
+  }
405
+  _thSendResponse(kHideStatusCmdId);
406
+}
407
+
408
+void cmdIf::_thDoClose( const cmd_t* cmd )
409
+{
410
+  _thStatusMsg("Closing ... ");
411
+
412
+  if( cmTimeLineFinalize(&_tlH) != kOkTlRC )
413
+  {
414
+    _thErrorMsg("Time line finalize failed.");
415
+  }
416
+
417
+  _thSendResponse(kHideStatusCmdId);
418
+}
419
+
420
+void cmdIf::_thDoSelectSeq( const cmd_t* cmd )
421
+{
422
+  _thStatusMsg("Selecting Sequence:%i ",cmd->value);
423
+
424
+  _curSeqId = cmInvalidId;
425
+  if( cmTimeLineSeqNotify(_tlH,cmd->value) != kOkTlRC )
426
+    _thErrorMsg("Sequence selection failed.");
427
+  else
428
+    _curSeqId = cmd->value;
429
+
430
+  _thSendResponse(kHideStatusCmdId);
431
+}
432
+
433
+void cmdIf::_thDoAfLoad( const cmd_t* cmd )
434
+{
435
+  _thStatusMsg("Loading Audio File: '%s'",cmd->u.string);
436
+
437
+  cmAfmFileH_t afH = cmAfmFileNullHandle;
438
+
439
+  if( cmAfmFileOpen(_afmH,&afH,cmd->u.string, cmd->value, NULL ) != kOkAfmRC )
440
+    _thErrorMsg("Audio file load failed on '%s'.",cmd->u.string);
441
+  else
442
+  {
443
+    double   msPerSummaryPt      = 50.0;
444
+    unsigned samplesPerSummaryPt = (unsigned)floor(cmAfmFileInfo(afH)->srate * msPerSummaryPt / 1000.0);
445
+
446
+    if( cmAfmFileSummarize(afH,samplesPerSummaryPt) != kOkAfmRC )
447
+      _thErrorMsg("Audio file summarization failed on '%s'.",cmd->u.string);
448
+    else
449
+      _thSendResponse(kAfLoadCmdId,cmd->u.string,cmd->value);
450
+  }
451
+
452
+  _thSendResponse(kHideStatusCmdId);
453
+}
454
+
455
+void cmdIf::_thDoScore( const cmd_t* cmd )
456
+{
457
+  _thStatusMsg("Loading Score File: '%s'",cmd->u.string);
458
+    
459
+  if( cmScoreInitialize(_ctx,&_scH,cmd->u.string,0,NULL,0,_thSendScoreMsg,this,cmSymTblNullHandle) != kOkScRC )
460
+    _thErrorMsg("Score open failed on '%s'.",cmStringNullGuard(cmd->u.string));
461
+  else
462
+  {
463
+    // Make notification callbacks for all score records to _thSendScoreMsg()
464
+    // _thSendScoreMsg() then enqueues msg's into _outQueH which are picked
465
+    // up by the idle handler
466
+    cmScoreSeqNotify(_scH);
467
+  }
468
+  _thSendResponse(kHideStatusCmdId);
469
+}
470
+
471
+void cmdIf::_thDoGenOnsetMarks( const cmd_t* cmd )
472
+{
473
+  if( !cmTimeLineIsValid(_tlH) )
474
+    return;
475
+
476
+  _thStatusMsg("Generating Onset Markers.");
477
+
478
+  // makes notification callbacks to _thSendTimeLineMsg()
479
+  if( cmTimeLineGenOnsetMarks(_tlH,_curSeqId) != kOkTlRC )
480
+    _thErrorMsg("Onset marker generation failed.");
481
+  else
482
+    cmTimeLineSeqNotify(_tlH,_curSeqId);
483
+
484
+  _thSendResponse(kHideStatusCmdId);
485
+}
486
+
487
+void cmdIf::_thDoDelOnsetMarks( const cmd_t* cmd )
488
+{
489
+  if( !cmTimeLineIsValid(_tlH) )
490
+    return;
491
+
492
+  _thStatusMsg("Deleting Onset Markers.");
493
+
494
+  // makes notification callbacks to _thSendTimeLineMsg()
495
+  if( cmTimeLineDeleteOnsetMarks(_tlH,_curSeqId) != kOkTlRC )
496
+    _thErrorMsg("Onset marker deletion failed.");
497
+  
498
+  _thSendResponse(kHideStatusCmdId);
499
+}
500
+
501
+/*
502
+void cmdIf::_thErrorMsg(  const char* fmt, va_list vl )
503
+{ 
504
+  const cmChar_t* s = cmTsVPrintf(fmt,vl);
505
+  _thSendResponse(kErrMsgCmdId,s); 
506
+  cmTsFreeStr(s);
507
+}
508
+*/
509
+void cmdIf::_thErrorMsg(  const char* fmt, ... )
510
+{
511
+  va_list vl,vl1;
512
+  va_start(vl,fmt);
513
+  va_copy(vl1,vl);
514
+
515
+  int n = vsnprintf(NULL,0,fmt,vl);
516
+  char b[n+1];
517
+  vsnprintf(b,n+1,fmt,vl1);
518
+  _thSendResponse(kErrMsgCmdId,b);   
519
+
520
+  va_end(vl1);
521
+  va_end(vl);
522
+}
523
+
524
+/*
525
+void cmdIf::_thStatusMsg( const char* fmt, va_list vl )
526
+{ 
527
+  const cmChar_t* s = cmTsVPrintf(fmt,vl);
528
+  _thSendResponse(kShowStatusCmdId,s); 
529
+  cmTsFreeStr(s);
530
+}
531
+*/
532
+
533
+void cmdIf::_thStatusMsg( const char* fmt, ... )
534
+{
535
+  va_list vl,vl1;
536
+  va_start(vl,fmt);
537
+  va_copy(vl1,vl);
538
+
539
+  int n = vsnprintf(NULL,0,fmt,vl);
540
+  char b[n+1];
541
+  vsnprintf(b,n+1,fmt,vl1);
542
+  _thSendResponse(kShowStatusCmdId,b); 
543
+  va_end(vl1);
544
+  va_end(vl);
545
+}
546
+
547
+
548
+void cmdIf::_thSendResponse( cmdId_t id, const char* str, unsigned value )
549
+{ 
550
+  if( _enqueue( _outQueH, id, value, str, str==NULL ? 0 : strlen(str)+1 ) != kOkRC )
551
+  {
552
+    _thErrorMsg("Response send failed.");
553
+  }
554
+}
555
+
556
+void cmdIf::_thSendTimeLineMsg( void* arg, const void* msg, unsigned byteCnt )
557
+{
558
+  cmdIf* p = (cmdIf*)arg;
559
+  if( cmTs1p1cIsValid( p->_outQueH ) )
560
+    if( p->_enqueue( p->_outQueH, kTimeLineMsgCmdId, 0, msg, byteCnt ) != kOkRC )
561
+      p->_thErrorMsg("Time Line enqueue failed on response queue.");
562
+}
563
+
564
+void cmdIf::_thSendScoreMsg( void* arg, const void* msg, unsigned byteCnt )
565
+{
566
+  cmdIf* p = (cmdIf*)arg;
567
+  if( cmTs1p1cIsValid( p->_outQueH ) )
568
+    if( p->_enqueue( p->_outQueH, kScoreMsgCmdId, 0, msg, byteCnt ) != kOkRC )
569
+      p->_thErrorMsg("Score msg enqueue failed on response queue.");
570
+}
571
+
572
+
573
+//----------------------------------------------------------------------------------------
574
+// Thread Independent Functions
575
+//----------------------------------------------------------------------------------------
576
+
577
+
578
+cmdIf::rc_t cmdIf::_enqueue( cmTs1p1cH_t qH, cmdId_t id, unsigned value, const void* data, unsigned byteCnt )
579
+{
580
+  cmThRC_t thRC;
581
+  rc_t     rc = kOkRC;
582
+  cmd_t    c;
583
+
584
+  assert( (byteCnt==0 && data==NULL) || (byteCnt!=0 && data!=NULL) );
585
+
586
+  c.id       = id;
587
+  c.byteCnt  = byteCnt;
588
+  c.value    = value;
589
+  c.u.msg    = NULL;
590
+  
591
+  if( byteCnt )
592
+  {
593
+    // memory allocated here must be deleted after the record is dequeued
594
+    c.u.string = cmMemAlloc(char,byteCnt);
595
+    memcpy(c.u.msg,data,byteCnt);
596
+  }
597
+
598
+  //printf("enq %s id:%i n:%i msg:%p\n", cmHandlesAreEqual(qH,_outQueH) ? "thr->app" : "app->thr", c.id,c.byteCnt,c.u.string);
599
+
600
+  if((thRC = cmTs1p1cEnqueueMsg(qH,&c,sizeof(c))) != kOkThRC )
601
+  {
602
+    if( byteCnt )
603
+      cmMemFree(c.u.string);
604
+
605
+    rc = kCmdFailRC;
606
+  }
607
+
608
+  return rc;
609
+}
610
+
611
+
612
+//----------------------------------------------------------------------------------------
613
+void cmdIf::_onTimeLineObjSelected( unsigned tlObjId )
614
+{
615
+  const cmTlObj_t* mop;
616
+  if((mop = cmTimeLineIdToObj(_tlH,cmInvalidId,tlObjId)) == NULL )
617
+  {
618
+    cmErrMsg(&_err,kCmdFailRC,"Unexpected invalid time line marker id '%i'.",tlObjId);
619
+    return;
620
+  }
621
+
622
+  const cmTlAudioFile_t* afp = cmTimeLineAudioFileAtTime(_tlH, mop->seqId, mop->seqSmpIdx );
623
+  const cmTlMidiFile_t*  mfp = cmTimeLineMidiFileAtTime( _tlH, mop->seqId, mop->seqSmpIdx );
624
+  const cmTlMidiEvt_t*   mep = cmTimeLineMidiEvtAtTime(  _tlH, mop->seqId, mop->seqSmpIdx );
625
+
626
+  if( afp != NULL )
627
+    printf("%s\n",afp->fn);
628
+
629
+  if( mfp != NULL )
630
+    printf("%s : %i\n",mfp->fn,mop->seqSmpIdx);
631
+
632
+  if( mep != NULL )
633
+  {
634
+    if( mep->msg->status == kNoteOnMdId )
635
+      printf("%s : %i\n",cmMidiToSciPitch(mep->msg->u.chMsgPtr->d0,NULL,0),mep->obj.seqSmpIdx);
636
+    else
637
+      printf("midi:%i\n",mep->msg->status);
638
+  }
639
+}
640
+
641
+//----------------------------------------------------------------------------------------
642
+void cmdIf::testStub()
643
+{
644
+  //ed_main();
645
+  //cmScAlignScanMarkers(_err.rpt, _tlH, _scH );
646
+  //sc_main(_scH,_tlH);
647
+  cmScorePrintLoc(_scH);
648
+}
649
+
650
+

+ 211
- 0
src/tlCtl/cmdIf.h View File

@@ -0,0 +1,211 @@
1
+#ifndef cmdIf_h
2
+#define cmdIf_h
3
+
4
+class Fl_Output;
5
+
6
+
7
+// This class allows the 'model' to run independently
8
+// from the user interface. This eliminates problems with
9
+// application unresponsiveness which would arise from
10
+// executing compute intensive operations from UI control or
11
+// menu callback functions.  It also allows a progress
12
+// or status bar to be shown while the model operation
13
+// is in progress.
14
+
15
+// The class works by enqueueing all incoming commands
16
+// into a thread-safe queue. An internal worker thread
17
+// executes the commands in the order they are received
18
+// and thereby changes the state of the model.
19
+
20
+// The results of model changes are posted to a second
21
+// thread-safe queue.  These responses are picked
22
+// up by the onIdle() member and dispatched to an
23
+// object  with a cmIfRspdr interface.  Note that because
24
+// the onIdle() function is called from the applications
25
+// idle handler the callbacks to the cmIfRspdr are
26
+// always in the application thread and can therefore
27
+// safely interact with any application data constructs.
28
+
29
+// All calls to this object and all callbacks from it,
30
+// therefore occur in the application thread.
31
+
32
+
33
+class cmdIfRspdr
34
+{
35
+ public:
36
+  virtual ~cmdIfRspdr(){}
37
+  virtual void cmdIfShowStatusMsg( const char* msg ) = 0;
38
+  virtual void cmdIfHideStatus() = 0;
39
+  virtual void cmdIfErrorMsg( const char* msg ) = 0;
40
+  virtual void cmdIfTimeLineMsg( const void* msg, unsigned msgByteCnt ) = 0;
41
+  virtual void cmdIfAudioFileLoad( unsigned fileId ) = 0;
42
+  virtual void cmdIfScoreMsg(    const void* msg, unsigned msgByteCnt ) = 0;
43
+
44
+  virtual void cmdIfOnTimeLineMarkerSelect( unsigned markerId ) = 0;
45
+  virtual void cmdIfOnTimeLineMidiEvtSelect(unsigned midiEvtId ) = 0;
46
+  virtual void cmdIfOnScoreBarSelect(       unsigned scoreIndex ) = 0;
47
+
48
+
49
+};
50
+
51
+class cmdIf
52
+{
53
+ public:
54
+
55
+  typedef enum
56
+  {
57
+    kOkRC,
58
+    kCmdFailRC,
59
+    kCmdEnqueueFailRC
60
+  } rc_t;
61
+
62
+  cmdIf( cmCtx_t* ctx, cmdIfRspdr* rspdr, const cmChar_t* audioPath=NULL );
63
+  virtual ~cmdIf();
64
+
65
+  // Open a time line.
66
+  rc_t         open( const cmChar_t* fn );
67
+
68
+  // Close the time line.
69
+  rc_t         close();
70
+
71
+  // Time line interface 
72
+  const cmChar_t*        tlFileName() const;
73
+  const cmTlObj_t*       tlObjIdToPtr( unsigned tlObjId ) const;
74
+  const cmTlMidiFile_t*  tlMidiFileObjPtr(  const cmTlObj_t* op ) const;
75
+  const cmTlAudioFile_t* tlAudioFileObjPtr( const cmTlObj_t* op ) const;
76
+  const cmTlMidiEvt_t*   tlMidiEvtObjPtr(   const cmTlObj_t* op ) const;
77
+  const cmTlAudioEvt_t*  tlAudioEvtObjPtr(  const cmTlObj_t* op ) const;
78
+  const cmTlMarker_t*    tlMarkerObjPtr(    const cmTlObj_t* op ) const;
79
+
80
+  const cmChar_t*         scoreFileName() const;
81
+  const cmScoreEvt_t*     scoreEventIdToPtr( unsigned scEvtId ) const;
82
+  const cmScoreSection_t* scoreSectionIdToPtr( unsigned scSectId ) const;
83
+
84
+  // Make a time line sequence active.
85
+  rc_t         selectSequence( unsigned id );
86
+
87
+  // Load an audio file into the audio file mgr.
88
+  // If an audio file path was set via setAudioFilePath() then
89
+  // the directories referenced by 'fn' will be replaced by
90
+  // the previously set audio file path.
91
+  rc_t         audioFileLoad( const cmChar_t* fn, unsigned appFileId );
92
+
93
+  // Return the audio file handle assigned to appFileId.
94
+  cmAfmFileH_t audioFileHandle( unsigned appFileId );
95
+
96
+  // Set the audio file location.
97
+  void         setAudioFilePath( const cmChar_t* path ); 
98
+
99
+  // Assign a score file
100
+  rc_t         setScore( const cmChar_t* scoreFn );
101
+
102
+  // Set the current score location
103
+  void         setScoreLocation( unsigned locIdx, unsigned smpIdx, unsigned pitch, unsigned vel );
104
+
105
+  // Set the value of a score variable
106
+  void         setScoreVarValue( unsigned locIdx, unsigned varId, double value );
107
+
108
+  // Set the performed dynamic level of a score event.
109
+  void         setScoreDynLevel( unsigned evtIdx, unsigned dynLvl );
110
+
111
+  void         onTimeLineMarkerSelected( unsigned markerTlId );
112
+  void         onTimeLineMidiEvtSelected( unsigned midiEvtTlId );
113
+  void         onScoreBarSelected( unsigned scoreIndex );
114
+
115
+  // Generate or delete Audio/MIDI onset markers.
116
+  rc_t         generateOnsetMarks();
117
+  rc_t         deleteOnsetMarks();
118
+
119
+  // True if the worker thread is running.
120
+  bool isBusy() const;
121
+  
122
+  // Called by the application to dequeue messages via callbacks to 
123
+  // the cmdIfRspdr.
124
+  void onIdle();
125
+  
126
+  void testStub();
127
+    
128
+ private:
129
+
130
+  // Id's used by cmd_t 
131
+  typedef enum
132
+  {
133
+    kInvalidCmdId,      // 0
134
+    kOpenCmdId,         // 1  app->thread
135
+    kCloseCmdId,        // 2  app->thread
136
+    kSelectSeqCmdId,    // 3  app->thread
137
+    kAfLoadCmdId,       // 4  app->thread and thread->app
138
+    kScoreCmdId,        // 5  app->thread    
139
+    kShowStatusCmdId,   // 6  thread->app
140
+    kHideStatusCmdId,   // 7  thread->app
141
+    kErrMsgCmdId,       // 8  thread->app
142
+    kTimeLineMsgCmdId,  // 9  thread->app
143
+    kScoreMsgCmdId,     //10  thread->app
144
+    kGenOnsetMarksCmdId,
145
+    kDelOnsetMarksCmdId
146
+
147
+  } cmdId_t;
148
+
149
+  // Messages are passed between the app and the worker thread
150
+  // and v.v. using this record format.  Note that the u.msg
151
+  // field is always dynamically allocated by _enqueue() 
152
+  // and must be released following the dequeue operation.
153
+  typedef struct cmd_str
154
+  {
155
+    cmdId_t  id;      // cmdId
156
+    unsigned byteCnt; // length of msg
157
+    unsigned value;   // msg value
158
+
159
+    union 
160
+    {
161
+      void* msg;     // msg[byteCnt] 
162
+      char* string;  // string[byteCnt]
163
+    } u;
164
+  } cmd_t;
165
+
166
+  cmCtx_t*    _ctx;        //
167
+  cmErr_t     _err;        // 
168
+  cmThreadH_t _thH;        // worker thread
169
+  cmTs1p1cH_t _cmdQueH;    // app->model
170
+  cmTs1p1cH_t _outQueH;    // model->appl
171
+  cmTlH_t     _tlH;        // time line handle    
172
+  cmAfmH_t    _afmH;       // audio file manager
173
+  cmScH_t     _scH;        // score handle
174
+  cmChar_t*   _afPath;     // 
175
+  cmdIfRspdr* _rspdr;      // 
176
+  unsigned    _curSeqId;   // seqId of last selected sequence
177
+
178
+
179
+  // Functions called from the app thread.
180
+  rc_t _sendCmd( cmdId_t id, unsigned value=0, const char* str=NULL );
181
+  void _releaseQue( cmTs1p1cH_t* queHPtr );
182
+
183
+  // Functions called from the worker thread
184
+  static bool _thFunc( void* arg );
185
+  void        _thDoOpen(      const cmd_t* cmd );
186
+  void        _thDoClose(     const cmd_t* cmd );
187
+  void        _thDoSelectSeq( const cmd_t* cmd );
188
+  void        _thDoAfLoad(    const cmd_t* cmd );
189
+  void        _thDoScore(     const cmd_t* cmd );
190
+  void        _thDoGenOnsetMarks( const cmd_t* cmd );
191
+  void        _thDoDelOnsetMarks( const cmd_t* cmd );
192
+
193
+  //void        _thErrorMsg(    const char*  fmt, va_list vl );
194
+  void        _thErrorMsg(    const char*  fmt, ... );
195
+  //void        _thStatusMsg(   const char*  fmt, va_list vl );
196
+  void        _thStatusMsg(   const char*  fmt, ... );
197
+  void        _thSendResponse( cmdId_t id, const char* str = NULL, unsigned value=0 );
198
+  static void _thSendTimeLineMsg( void* arg, const void* msg, unsigned byteCnt );
199
+  static void _thSendScoreMsg(    void* arg, const void* msg, unsigned byteCnt );
200
+
201
+  // Thread independent functions 
202
+  rc_t _enqueue( cmTs1p1cH_t qH, cmdId_t id, unsigned value, const void* msg, unsigned msgByteCnt );
203
+
204
+
205
+  // Print context information for selected time line objects
206
+  void _onTimeLineObjSelected( unsigned tlObjId );
207
+
208
+};
209
+
210
+
211
+#endif

+ 62
- 0
src/tlCtl/gvHashFunc.cpp View File

@@ -0,0 +1,62 @@
1
+#include "cmPrefix.h"
2
+#include "cmGlobal.h"
3
+#include "cmFloatTypes.h"
4
+#include "cmRpt.h"
5
+#include "cmErr.h"
6
+#include "cmCtx.h"
7
+#include "cmTime.h"
8
+#include "cmMidi.h"
9
+#include "cmGr.h"
10
+#include "gvHashFunc.h"
11
+
12
+void gvRoundHashValueFunc(  void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
13
+{
14
+  snprintf(label,labelCharCnt,"%i",(int)round(value));
15
+}
16
+
17
+void gvMidiSciPitchValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
18
+{
19
+  assert( label != NULL && labelCharCnt > 0 );
20
+
21
+  if( labelCharCnt > 0 )
22
+    label[0] = 0;
23
+
24
+  if( 0 <= value && value <= 127 )
25
+    cmMidiToSciPitch((cmMidiByte_t)floor(value), label, labelCharCnt );
26
+  else
27
+  {
28
+    if( labelCharCnt > 3 )
29
+      strcpy(label,"?");
30
+  }
31
+}
32
+void gvMinSecMsHashValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value )
33
+{
34
+  gvHashFuncArg* p = (gvHashFuncArg*)arg;
35
+  
36
+  int min=0,sec=0,ms=0;
37
+
38
+  double smpPerMin = p->sampleRate() * 60.0;
39
+  double smpPerMs  = p->sampleRate() / 1000.0;
40
+
41
+  if( value > smpPerMin ) 
42
+  {
43
+    min    = (int)floor( value / smpPerMin );
44
+    value -= min * smpPerMin;
45
+  }
46
+
47
+  if( value > p->sampleRate() )
48
+  {
49
+    sec    = (int)floor( value / p->sampleRate() );
50
+    value -= sec * p->sampleRate();
51
+  }
52
+
53
+
54
+  if( value > smpPerMs )
55
+  {
56
+    ms     = (int)floor( value / smpPerMs );
57
+    value -= ms * smpPerMs;
58
+  }
59
+
60
+  snprintf(label,labelCharCnt,"%i:%2i:%2i",min,sec,ms); 
61
+}
62
+

+ 18
- 0
src/tlCtl/gvHashFunc.h View File

@@ -0,0 +1,18 @@
1
+#ifndef gvHashFunc_h
2
+#define gvHashFunc_h
3
+
4
+class gvHashFuncArg
5
+{
6
+ public:
7
+  virtual ~gvHashFuncArg(){}
8
+  virtual double sampleRate() const = 0;
9
+
10
+};
11
+
12
+extern "C" {
13
+void gvRoundHashValueFunc(    void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
14
+void gvMinSecMsHashValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
15
+void gvMidiSciPitchValueFunc( void* arg, cmChar_t* label, unsigned labelCharCnt, cmGrV_t value );
16
+}
17
+
18
+#endif

+ 388
- 0
src/tlCtl/tlCtl.cpp View File

@@ -0,0 +1,388 @@
1
+#include <FL/Fl.H>
2
+#include <FL/Fl_Widget.H>
3
+#include <FL/Fl_Window.H>
4
+#include <FL/Fl_Menu_Bar.H>
5
+#include <FL/Fl_Group.H>
6
+#include <FL/fl_draw.H>
7
+
8
+#include <vector>
9
+#include "Fl_Splitter.h"
10
+#include "Fl_CbLinker.h"
11
+
12
+#include "cmPrefix.h"
13
+#include "cmGlobal.h"
14
+#include "cmFloatTypes.h"
15
+#include "cmRpt.h"
16
+#include "cmErr.h"
17
+#include "cmCtx.h"
18
+#include "cmMem.h"
19
+#include "cmMallocDebug.h"
20
+#include "cmLinkedHeap.h"
21
+#include "cmFileSys.h"
22
+#include "cmThread.h"
23
+#include "cmText.h"
24
+#include "cmPrefs.h"
25
+#include "cmSymTbl.h"
26
+#include "cmTime.h"
27
+#include "cmMidi.h"
28
+#include "cmMidiFile.h"
29
+#include "cmAudioFile.h"
30
+#include "cmAudioFileMgr.h"
31
+#include "cmTimeLine.h"
32
+#include "cmScore.h"
33
+#include "cmTakeSeqBldr.h"
34
+#include "cmGr.h"
35
+#include "cmGrDevCtx.h"
36
+#include "cmGrPlot.h"
37
+#include "cmGrPage.h"
38
+#include "cmGrFltk.h"
39
+#include "gvHashFunc.h"
40
+#include "cmGrTlFltk.h"
41
+#include "cmGrScFltk.h"
42
+#include "cmGrTksbFltk.h"
43
+#include "cmGrTksrFltk.h"
44
+#include "cmGr2dFltk.h"
45
+#include "cmdIf.h"
46
+#include "tlCtl.h"
47
+
48
+//----------------------------------------------------------------------------------------------------
49
+//----------------------------------------------------------------------------------------------------
50
+//----------------------------------------------------------------------------------------------------
51
+
52
+class tlStatusWnd : public Fl_Window
53
+{
54
+ public:
55
+  tlStatusWnd(int w, int h, const char* label);
56
+  virtual ~tlStatusWnd();
57
+
58
+  void display( const char* msg );
59
+  virtual void draw();
60
+
61
+ private:
62
+  char* _msg;
63
+  enum { kBorder = 10 };
64
+  
65
+};
66
+
67
+tlStatusWnd::tlStatusWnd(int w, int h, const char* label)
68
+  : Fl_Window(w,h,label),_msg(NULL)
69
+{
70
+  end();
71
+  clear_border();
72
+}
73
+
74
+tlStatusWnd:: ~tlStatusWnd()
75
+{
76
+  cmMemFree(_msg);
77
+}
78
+
79
+void tlStatusWnd::display( const char* msg )
80
+{
81
+  bool fl = false;
82
+  int border = 2*kBorder;
83
+    
84
+  // store the string
85
+  _msg = cmMemResizeStr(_msg,msg);
86
+
87
+  // The offscreen drawing context is probably not necesary.
88
+  // However if a font change was applied then it would guarantee that
89
+  // fl_measure() used the correct font.
90
+  Fl_Offscreen os = fl_create_offscreen(w(),h());
91
+  fl_begin_offscreen(os);
92
+
93
+  // BEWARE: fl_measure uses 'ww' on input.
94
+  int ww=0,hh=0;
95
+  fl_measure(_msg,ww,hh,0);
96
+  fl_end_offscreen();
97
+  fl_delete_offscreen(os);
98
+  
99
+  if( ww+border < w()  )
100
+    ww = w();
101
+  else
102
+  {
103
+    ww += border;
104
+    fl = true;
105
+  }
106
+
107
+  if( hh+border < h() )
108
+    hh = h();
109
+  else
110
+  {
111
+    hh = hh+border;
112
+    fl = true;
113
+  }
114
+
115
+
116
+  if(fl)
117
+    size(ww,hh);
118
+
119
+  int xx = parent()->w()/2 - ww/2;
120
+  int yy = parent()->h()/2 - hh/2;
121
+  position(xx,yy);
122
+
123
+
124
+  set_modal();
125
+  show();
126
+}
127
+
128
+void tlStatusWnd::draw()
129
+{
130
+  // BEWARE: fl_measure uses 'ww' on input.
131
+  int ww=0,hh=0;
132
+  fl_measure(_msg,ww,hh,0);
133
+
134
+  int xx =  w()/2 - ww/2;
135
+  int yy =  h()/2;
136
+
137
+  fl_rect(0,0,w(),h());
138
+  fl_draw(_msg,xx,yy);
139
+
140
+}
141
+
142
+
143
+//----------------------------------------------------------------------------------------------------
144
+//----------------------------------------------------------------------------------------------------
145
+//----------------------------------------------------------------------------------------------------
146
+
147
+ 
148
+tlCtl::tlCtl( cmCtx_t* ctx, Fl_Window* app, Fl_Menu_Bar* menuBar, tlCtlRspdr* rspdr )
149
+  : _ctx(ctx),_rspdr(rspdr),
150
+    _cmdIf(NULL),_tlCtlr(NULL),_scCtlr(NULL),_tksbCtlr(NULL),_tksrCtlr(NULL),_2dCtlr(NULL),
151
+    _statusWnd(NULL),_menu(menuBar)
152
+{
153
+  cmErrSetup(&_err,&ctx->rpt,"tlCtl");
154
+  _cmdIf = new cmdIf( ctx,this );
155
+  app->add(_statusWnd = new tlStatusWnd(app->w()/2,app->h()/2,"Status"));
156
+
157
+}
158
+
159
+tlCtl::~tlCtl()
160
+{
161
+  delete _cmdIf;
162
+  delete _tlCtlr;
163
+  delete _scCtlr;
164
+  delete _tksbCtlr;
165
+  delete _tksrCtlr;
166
+  delete _2dCtlr;
167
+  delete _statusWnd;
168
+}
169
+
170
+Fl_Widget* tlCtl::initTimeLineCtlr( int x, int y, int w, int h )
171
+{
172
+  delete _tlCtlr;
173
+  _tlCtlr = NULL;
174
+  return _tlCtlr = new cmGrTlFltk(_ctx,_cmdIf,_menu,x,y,w,h);
175
+}
176
+
177
+Fl_Widget* tlCtl::initScoreCtlr( int x, int y, int w, int h )
178
+{
179
+  delete _scCtlr;
180
+  _scCtlr = NULL;
181
+  return _scCtlr = new cmGrScFltk(_ctx,_cmdIf,_menu,x,y,w,h);
182
+}
183
+
184
+Fl_Widget* tlCtl::initTakeSeqBldrCtlr( int x, int y, int w, int h )
185
+{
186
+  delete _tksbCtlr;
187
+  _tksbCtlr = NULL;
188
+  return _tksbCtlr = new cmGrTksbFltk(_ctx,_cmdIf,_menu,x,y,w,h);
189
+}
190
+
191
+Fl_Widget* tlCtl::initTakeSeqRendCtlr( int x, int y, int w, int h )
192
+{
193
+  delete _tksrCtlr;
194
+  _tksrCtlr = NULL;
195
+  return _tksrCtlr = new cmGrTksrFltk(_ctx,_cmdIf,_menu,x,y,w,h);
196
+}
197
+
198
+Fl_Widget* tlCtl::init2dCtlr( int x, int y, int w, int h )
199
+{
200
+  delete _2dCtlr;
201
+  _2dCtlr = NULL;
202
+  return _2dCtlr = new cmGr2dFltk(_ctx,_menu,x,y,w,h);
203
+}
204
+
205
+
206
+void tlCtl::openTlFile( const cmChar_t* fn )
207
+{ 
208
+  if( fn!=NULL && _tlCtlr != NULL )
209
+    _cmdIf->open(fn);
210
+}
211
+
212
+void tlCtl::openScoreFile( const cmChar_t* fn )
213
+{
214
+  if( fn!=NULL && _scCtlr != NULL )
215
+    _cmdIf->setScore(fn);
216
+}
217
+
218
+void tlCtl::openTakeSeqBldr( void* v )
219
+{
220
+  if( v!=NULL && _tksbCtlr != NULL )
221
+    _tksbCtlr->setTksbHandle(v);
222
+}
223
+
224
+void tlCtl::openTakeSeqRend( void* v )
225
+{
226
+  if( v!=NULL && _tksrCtlr != NULL )
227
+    _tksrCtlr->setTksbHandle(v);
228
+}
229
+
230
+void tlCtl::setAudioFilePath( const cmChar_t* path )
231
+{
232
+  if( path!=NULL )
233
+    _cmdIf->setAudioFilePath(path);
234
+}
235
+
236
+void tlCtl::setAudioFileCursor( unsigned smpIdx )
237
+{
238
+  if( _tlCtlr != NULL )
239
+    _tlCtlr->setAudioFileCursor(smpIdx);
240
+}
241
+
242
+void tlCtl::setTimeLineSelectBar( unsigned barNumb )
243
+{
244
+  if( _tlCtlr != NULL )
245
+    _tlCtlr->selectBar(barNumb);
246
+}
247
+
248
+void tlCtl::setScoreSelectBar( unsigned barNumb )
249
+{
250
+  if( _scCtlr != NULL )
251
+    _scCtlr->selectBar(barNumb);
252
+}
253
+
254
+void tlCtl::setScoreLocation( unsigned locIdx, unsigned smpIdx, unsigned pitch, unsigned vel )
255
+{
256
+  _cmdIf->setScoreLocation( locIdx, smpIdx, pitch, vel );
257
+}
258
+
259
+void tlCtl::setScoreVarValue( unsigned locIdx, unsigned varId, double value )
260
+{
261
+  _cmdIf->setScoreVarValue( locIdx, varId, value );
262
+}
263
+
264
+void tlCtl::setScoreDynLevel( unsigned evtIdx, unsigned dynLvl )
265
+{
266
+  _cmdIf->setScoreDynLevel(evtIdx,dynLvl);
267
+}
268
+
269
+void tlCtl::refreshTakeSeqRend()
270
+{
271
+  if( _tksrCtlr != NULL )
272
+    _tksrCtlr->refresh();
273
+}
274
+
275
+void tlCtl::onIdle()
276
+{ _cmdIf->onIdle(); }
277
+
278
+
279
+void tlCtl::cmdIfShowStatusMsg( const char* msg )
280
+{ 
281
+  _statusWnd->display(msg); 
282
+}
283
+
284
+void tlCtl::cmdIfHideStatus()
285
+{
286
+  _statusWnd->hide();
287
+  _statusWnd->set_non_modal();
288
+}
289
+
290
+void tlCtl::cmdIfErrorMsg( const char* msg )
291
+{ 
292
+  cmErrMsg(&_err,1,"%s",msg); 
293
+}
294
+
295
+void tlCtl::cmdIfTimeLineMsg( const void* msg, unsigned msgByteCnt )
296
+{
297
+  switch( _tlCtlr->recvTimeLineMsg(msg,msgByteCnt) )
298
+  {
299
+    case kInitMsgTlId:
300
+      if( _rspdr!= NULL && _cmdIf->tlFileName() != NULL )
301
+        _rspdr->tlCtlNewTimeLineFile(this,_cmdIf->tlFileName());
302
+      break;
303
+
304
+    case kDoneMsgTlId:
305
+
306
+      if( _scCtlr != NULL && _tlCtlr != NULL )
307
+        _scCtlr->setSampleRate( _tlCtlr->sampleRate() );
308
+
309
+      _menu->parent()->redraw();
310
+
311
+      break;
312
+
313
+    default:
314
+      break;
315
+  }
316
+
317
+}
318
+
319
+void tlCtl::cmdIfAudioFileLoad( unsigned fileId )
320
+{  
321
+  _tlCtlr->recvAudioFileLoad(fileId);  
322
+}
323
+
324
+void tlCtl::cmdIfScoreMsg( const void* msg, unsigned msgByteCnt )
325
+{
326
+  assert( _scCtlr != NULL );
327
+
328
+
329
+  switch( _scCtlr->recvScoreMsg(msg,msgByteCnt) )
330
+  {
331
+    case kBeginMsgScId:
332
+      if( _rspdr!= NULL && _cmdIf->scoreFileName() != NULL )
333
+        _rspdr->tlCtlNewScoreFile(this,_cmdIf->scoreFileName());
334
+      break;
335
+
336
+    case kEndMsgScId:
337
+      _scCtlr->setSampleRate( _tlCtlr->sampleRate() );
338
+      _scCtlr->redraw();
339
+      break;
340
+
341
+      _menu->parent()->redraw();
342
+
343
+    default:
344
+      break;
345
+  }
346
+
347
+}
348
+
349
+void tlCtl::cmdIfOnTimeLineMarkerSelect( unsigned markerId )
350
+{
351
+  
352
+}
353
+
354
+void tlCtl::cmdIfOnTimeLineMidiEvtSelect( unsigned midiEvtId )
355
+{
356
+}
357
+
358
+void tlCtl::cmdIfOnScoreBarSelect( unsigned scoreIndex )
359
+{
360
+}
361
+
362
+
363
+unsigned tlCtl::timeLineSelectedMarkerId() const
364
+{
365
+  if( _tlCtlr==NULL)
366
+    return cmInvalidId;
367
+  return _tlCtlr->timeLineSelectedMarkerId();
368
+}
369
+
370
+unsigned tlCtl::scoreSelectedEleIndex() const
371
+{
372
+  if(_scCtlr==NULL)
373
+    return cmInvalidId;
374
+  return _scCtlr->scoreSelectedEleIndex();
375
+}
376
+
377
+unsigned tlCtl::tksbSelectedEleIndex() const
378
+{
379
+  if(_tksbCtlr==NULL)
380
+    return cmInvalidId;
381
+  return _tksbCtlr->scoreSelectedEleIndex();
382
+}
383
+
384
+
385
+void tlCtl::testStub() 
386
+{
387
+  _cmdIf->testStub();
388
+}

+ 99
- 0
src/tlCtl/tlCtl.h View File

@@ -0,0 +1,99 @@
1
+#ifndef tlCtl_h
2
+#define tlCtl_h
3
+
4
+class Fl_Menu_Bar;
5
+class cmGrTlFltk;
6
+class cmGrScFltk;
7
+class cmGrTksbFltk;
8
+class cmGrTksrFltk;
9
+class cmGr2dFltk;
10
+class tlStatusWnd;
11
+class tlCtl;
12
+
13
+class tlCtlRspdr
14
+{
15
+public:
16
+  virtual ~tlCtlRspdr(){}
17
+  virtual void tlCtlNewTimeLineFile( tlCtl* tlCtl, const cmChar_t* fn ) = 0;
18
+  virtual void tlCtlNewScoreFile(    tlCtl* tlCtl, const cmChar_t* fn ) = 0;
19
+  
20
+};
21
+
22
+class tlCtl : public cmdIfRspdr
23
+{
24
+public:
25
+  tlCtl( cmCtx_t* ctx, Fl_Window* app, Fl_Menu_Bar* menuBar, tlCtlRspdr* rspdr );
26
+  virtual ~tlCtl();
27
+
28
+  // 
29
+  // This group of functions represent commands from the application (kcApp) to the
30
+  // time-line control.
31
+  //
32
+
33
+  Fl_Widget* initTimeLineCtlr(    int x, int y, int w, int h );
34
+  Fl_Widget* initScoreCtlr(       int x, int y, int w, int h );
35
+  Fl_Widget* initTakeSeqBldrCtlr( int x, int y, int w, int h ); 
36
+  Fl_Widget* initTakeSeqRendCtlr( int x, int y, int w, int h );
37
+  Fl_Widget* init2dCtlr(          int x, int y, int w, int h ); 
38
+
39
+  void openTlFile( const cmChar_t* fn );
40
+  void openScoreFile( const cmChar_t* fn );
41
+  void openTakeSeqBldr( void* v );
42
+  void openTakeSeqRend( void* v );
43
+  void setAudioFilePath( const cmChar_t* path );
44
+  void setAudioFileCursor( unsigned smpIdx );
45
+  void setTimeLineSelectBar( unsigned barNumb );
46
+  void setScoreSelectBar( unsigned barNumb );
47
+
48
+  // Set the currrent score location
49
+  void setScoreLocation( unsigned locIdx, unsigned smpIdx, unsigned pitch, unsigned vel );
50
+
51
+  // Set the value of a score variable.
52
+  void setScoreVarValue( unsigned locIdx, unsigned varId, double value );
53
+
54
+  // Set the performed dynamic level of a score event.
55
+  void setScoreDynLevel( unsigned evtIdx, unsigned dynLvl );
56
+
57
+  void refreshTakeSeqRend();
58
+
59
+  void onIdle();
60
+
61
+  
62
+  //
63
+  // cmdIfRspdr Interface
64
+  //
65
+  // These functions are callbacks from cmdIf to communicate 
66
+  // from cmdIf processes to the UI or back to the engine.
67
+ 
68
+  virtual void cmdIfShowStatusMsg( const char* msg );
69
+  virtual void cmdIfHideStatus();
70
+  virtual void cmdIfErrorMsg( const char* msg );
71
+  virtual void cmdIfTimeLineMsg( const void* msg, unsigned msgByteCnt );
72
+  virtual void cmdIfAudioFileLoad( unsigned fileId );
73
+  virtual void cmdIfScoreMsg(    const void* msg, unsigned msgByteCnt );
74
+  virtual void cmdIfOnTimeLineMarkerSelect( unsigned markerId );
75
+  virtual void cmdIfOnTimeLineMidiEvtSelect(unsigned midiEvtId );
76
+  virtual void cmdIfOnScoreBarSelect(       unsigned scoreIndex );
77
+
78
+  unsigned timeLineSelectedMarkerId() const;
79
+  unsigned scoreSelectedEleIndex() const;
80
+  unsigned tksbSelectedEleIndex() const;
81
+  
82
+  void testStub();
83
+
84
+private:
85
+  cmErr_t         _err;
86
+  cmCtx_t*        _ctx;
87
+  tlCtlRspdr*     _rspdr;
88
+  cmdIf*          _cmdIf;
89
+  cmGrTlFltk*     _tlCtlr;
90
+  cmGrScFltk*     _scCtlr;
91
+  cmGrTksbFltk*   _tksbCtlr;
92
+  cmGrTksrFltk*   _tksrCtlr;
93
+  cmGr2dFltk*     _2dCtlr;
94
+  tlStatusWnd*    _statusWnd;
95
+  Fl_Menu_Bar*    _menu;
96
+};
97
+
98
+
99
+#endif

Loading…
Cancel
Save