[xiph-cvs] cvs commit: MTG soundboard.c

Monty xiphmont at xiph.org
Sun Feb 3 11:16:57 PST 2002



xiphmont    02/02/03 11:16:57

  Modified:    .        soundboard.c
  Log:
  minor fixes, added current vol indicator in tag playback list,
  improved locking around edit/playback

Revision  Changes    Path
1.6       +95 -63    MTG/soundboard.c

Index: soundboard.c
===================================================================
RCS file: /usr/local/cvsroot/MTG/soundboard.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- soundboard.c	2002/02/01 13:22:54	1.5
+++ soundboard.c	2002/02/03 19:16:56	1.6
@@ -2,7 +2,12 @@
 
    make Esc behavior correct in editing menus by using temp cue/tag storage
    tag list menu
-   proper locking around edit to prevent playback problems
+   sane arrow keying
+   autocompletion
+   logarhythmic fades
+   proper printing out of file loading issues
+   abstracted output
+   allow sample name/tag change in edit menus
 */
 #define _REENTRANT 1
 #include <stdlib.h>
@@ -30,7 +35,7 @@
 static char *lockfile="/tmp/beaverphonic/lock";
 //static char *installdir="/usr/local/beaverphonic/";
 static char *installdir="/home/xiphmont/MotherfishCVS/MTG/";
-#define VERSION "20020128.0"
+#define VERSION "20020203.0"
 
 enum menutype {MENU_MAIN,MENU_KEYPRESS,MENU_ADD,MENU_EDIT,MENU_OUTPUT,MENU_QUIT};
 
@@ -87,7 +92,8 @@
 
 /******** channel mappings.  All hardwired for now... ***********/
 // only OSS stereo builin for now
-#define MAX_CHANNELS 2
+#define MAX_OUPUT_CHANNELS 2
+#define MAX_INPUT_CHANNELS 2
 #define CHANNEL_LABEL_LENGTH 50
 int playback_bufsize=0;
 
@@ -97,11 +103,11 @@
   /* real stuff not here yet */
 } outchannel;
   
-static outchannel channel_list[MAX_CHANNELS]={
+static outchannel channel_list[MAX_OUPUT_CHANNELS]={
   {"offstage left",0},
   {"offstage right",0},
 };
-static int channel_count=MAX_CHANNELS;
+static int channel_count=MAX_OUPUT_CHANNELS;
 
 /******** label abstraction code; use this for all alloced strings
           that need to be saved to config file (shared or not) */
@@ -237,9 +243,9 @@
   double master_vol_target;
   double master_vol_slew;
 
-  double outvol_current[2][MAX_CHANNELS];
-  double outvol_target[2][MAX_CHANNELS];
-  double outvol_slew[2][MAX_CHANNELS];
+  double outvol_current[MAX_INPUT_CHANNELS][MAX_OUPUT_CHANNELS];
+  double outvol_target[MAX_INPUT_CHANNELS][MAX_OUPUT_CHANNELS];
+  double outvol_slew[MAX_INPUT_CHANNELS][MAX_OUPUT_CHANNELS];
 
 } tag;
 
@@ -264,11 +270,13 @@
 static void _alloc_tag_if_needed(int number){
   if(number>=tag_count){
     int prev=tag_count;
+    pthread_mutex_lock(&master_mutex);
     tag_count=number+1;
     tag_list=m_realloc(tag_list,sizeof(*tag_list)*tag_count);
     active_list=m_realloc(active_list,sizeof(*active_list)*tag_count);
     
     memset(tag_list+prev,0,sizeof(*tag_list)*(tag_count-prev));
+    pthread_mutex_unlock(&master_mutex);
   }
 }
 
@@ -373,6 +381,15 @@
 }
 
 int unload_sample(tag *t){
+  /* is this sample currently playing back? */
+  pthread_mutex_lock(&master_mutex);
+  if(t->activep){
+    int i;
+    for(i=0;i<active_count;i++)
+      if(active_list[i]==t)_playback_remove(i);
+  }
+  pthread_mutex_unlock(&master_mutex);
+
   /* unmap */
   if(t->basemap)
     munmap(t->basemap,
@@ -408,10 +425,15 @@
   if(number>=tag_count)return;
   tag_list[number].refcount--;
   if(tag_list[number].refcount==0){
-    if(tag_list[number].basemap)
-      unload_sample(tag_list+number);
-    release_label(tag_list[number].sample_path);
-    release_label(tag_list[number].sample_desc);
+    tag *t=tag_list+number;
+
+    if(t->basemap)
+      unload_sample(t); /* <- locked here; this gets it off the play
+                           list and eliminates any playback thread
+                           interdependancies; it can't get back on
+                           active play list if we're here */
+    release_label(t->sample_path);
+    release_label(t->sample_desc);
   }
   if(tag_list[number].refcount<0)
     tag_list[number].refcount=0;
@@ -471,7 +493,7 @@
   int  vol_master;
   long vol_ms;
   
-  int  outvol[2][MAX_CHANNELS];
+  int  outvol[MAX_INPUT_CHANNELS][MAX_OUPUT_CHANNELS];
 } mix;
 
 typedef struct {
@@ -492,23 +514,28 @@
   int i;
 
   if(cue_count==cue_storage){
+    pthread_mutex_lock(&master_mutex);
     cue_storage++;
     cue_storage*=2;
     cue_list=m_realloc(cue_list,cue_storage*sizeof(*cue_list));
+    pthread_mutex_unlock(&master_mutex);
   }
 
   /* copy insert */
+  pthread_mutex_lock(&master_mutex);
   if(cue_count-n)
     memmove(cue_list+n+1,cue_list+n,sizeof(*cue_list)*(cue_count-n));
   cue_count++;
 
   cue_list[n]=c;
+  pthread_mutex_unlock(&master_mutex);
 }
 
 /* inefficient.  delete one, shift-copy list, delete one, shift-copy
    list, delete one, gaaaah.  Not worth optimizing */
 static void _delete_cue_helper(int n){
   if(n>=0 && n<cue_count){
+    pthread_mutex_lock(&master_mutex);
     release_label(cue_list[n].label);
     release_label(cue_list[n].cue_text);
     release_label(cue_list[n].cue_desc);
@@ -516,6 +543,7 @@
     cue_count--;
     if(n<cue_count)
       memmove(cue_list+n,cue_list+n+1,sizeof(*cue_list)*(cue_count-n));
+    pthread_mutex_unlock(&master_mutex);
   }
 }
 
@@ -563,10 +591,10 @@
             c->tag,c->tag_create_p,
             c->mix.vol_master,
             c->mix.vol_ms,
-	    MAX_CHANNELS,
-	    2);
+	    MAX_OUPUT_CHANNELS,
+	    MAX_INPUT_CHANNELS);
     
-    for(i=0;i<MAX_CHANNELS;i++)
+    for(i=0;i<MAX_OUPUT_CHANNELS;i++)
       fprintf(f,"<%d %d>",c->mix.outvol[0][i],c->mix.outvol[1][i]);
     count=fprintf(f,"\n");
     if(count<1)return(-1);
@@ -620,7 +648,7 @@
         addnlstr("LOAD ERROR (CUE): parse error looking for value.",80,' ');
         return(-1);
       }
-      if(j<2)
+      if(j<MAX_INPUT_CHANNELS)
         c.mix.outvol[j][i]=v;
     }
     count=fscanf(f,"%c",&ch);
@@ -739,6 +767,7 @@
   int j,k;
 
   if(t->activep)return;
+  if(!t->basemap)return;
   t->activep=1;
   refresh();
 
@@ -761,7 +790,7 @@
   t->master_vol_target=c->mix.vol_master;
   t->master_vol_slew=_slew_ms(c->mix.vol_ms,0,c->mix.vol_master);
                              
-  for(j=0;j<MAX_CHANNELS;j++)
+  for(j=0;j<MAX_OUPUT_CHANNELS;j++)
     for(k=0;k<t->channels;k++){
       t->outvol_current[k][j]=0;
       t->outvol_target[k][j]=c->mix.outvol[k][j];
@@ -782,7 +811,7 @@
   t->master_vol_slew=_slew_ms(c->mix.vol_ms,t->master_vol_current,
                            c->mix.vol_master);
                              
-  for(j=0;j<MAX_CHANNELS;j++)
+  for(j=0;j<MAX_OUPUT_CHANNELS;j++)
     for(k=0;k<t->channels;k++){
       t->outvol_target[k][j]=c->mix.outvol[k][j];
       t->outvol_slew[k][j]=_slew_ms(c->mix.vol_ms,t->outvol_current[k][j],
@@ -792,7 +821,7 @@
 
 static inline void _next_sample(int16 *out){
   int i,j,k;
-  int staging[MAX_CHANNELS];
+  int staging[MAX_OUPUT_CHANNELS];
 
   memset(staging,0,sizeof(staging));
 
@@ -818,7 +847,7 @@
       }
 
       /* output split and mix */
-      for(k=0;k<MAX_CHANNELS;k++){
+      for(k=0;k<MAX_OUPUT_CHANNELS;k++){
         staging[k]+=value*t->outvol_current[j][k]*main_master_volume*.0001;
         
         t->outvol_current[j][k]+=t->outvol_slew[j][k];
@@ -870,7 +899,7 @@
   }
 
   /* declipping, conversion */
-  for(i=0;i<MAX_CHANNELS;i++){
+  for(i=0;i<MAX_OUPUT_CHANNELS;i++){
     if(channel_list[i].peak<fabs(staging[i]))
       channel_list[i].peak=fabs(staging[i]);
     if(staging[i]>32767.){
@@ -1220,6 +1249,7 @@
     break;
   default:
     if(f->edit){
+      pthread_mutex_lock(&master_mutex);
       switch(ff->type){
       case FORM_YESNO:
         {
@@ -1346,6 +1376,8 @@
         ret=c;
         break;
       }
+      pthread_mutex_unlock(&master_mutex);
+
     }else{
       ret=c;
     }
@@ -1358,7 +1390,7 @@
 void main_update_master(int n,int y){
   if(menu==MENU_MAIN){
     char buf[4];
-    if(n>100)n=100;
+    if(n>300)n=300;
     if(n<0)n=0;
 
     pthread_mutex_lock(&master_mutex);
@@ -1406,11 +1438,11 @@
 }
 
 #define todB_nn(x)   ((x)==0.f?-400.f:log((x))*8.6858896f)
-static int clip[MAX_CHANNELS];
+static int clip[MAX_OUPUT_CHANNELS];
 void main_update_outchannel_levels(int y){
   int i,j;
   if(menu==MENU_MAIN){
-    for(i=0;i<MAX_CHANNELS;i++){
+    for(i=0;i<MAX_OUPUT_CHANNELS;i++){
       int val;
       char buf[11];
       pthread_mutex_lock(&master_mutex);
@@ -1449,7 +1481,7 @@
   int i;
   char buf[80];
   if(menu==MENU_MAIN){
-    for(i=0;i<MAX_CHANNELS;i++){
+    for(i=0;i<MAX_OUPUT_CHANNELS;i++){
       move(y+i+1,4);
       sprintf(buf,"%2d: -Inf[          ]+0dB ",i);
       addstr(buf);
@@ -1529,7 +1561,8 @@
       for(i=0;i<active_count;i++){
         int loop;
         int ms;
-	char buf[8];
+	char buf[20];
+	int vol=active_list[i]->master_vol_current;
         label_number path;
         
         move(y+i,14);
@@ -1538,11 +1571,11 @@
         path=active_list[i]->sample_desc;
         
         if(loop)
-	  sprintf(buf,"[loop] ");
+	  snprintf(buf,20,"[loop %3d%%] ",vol);
         else
-	  sprintf(buf,"[%3ds] ",(ms+500)/1000);
+	  snprintf(buf,20,"[%3ds %3d%%] ",(ms+500)/1000,vol);
         addstr(buf);
-	addnlstr(label_text(path),55,' ');
+	addnlstr(label_text(path),60,' ');
       }
     }else{
       addstr("             ");
@@ -1550,7 +1583,7 @@
 
     for(i=active_count;i<last_tags;i++){
       move(y+i,14);
-      addnlstr("",55,' ');
+      addnlstr("",60,' ');
     }
 
     last_tags=active_count;
@@ -1577,7 +1610,7 @@
       if(cue_list[cue_list_number].tag==-1)break;
     cue_list_position++;
   }
-  main_update_cues(10+MAX_CHANNELS);
+  main_update_cues(10+MAX_OUPUT_CHANNELS);
 }
 
 void move_prev_cue(){
@@ -1586,7 +1619,7 @@
       if(cue_list[cue_list_number].tag==-1)break;
     cue_list_position--;
   }
-  main_update_cues(10+MAX_CHANNELS);
+  main_update_cues(10+MAX_OUPUT_CHANNELS);
 }
 
 int save_top_level(char *fn){
@@ -1634,15 +1667,15 @@
   attroff(A_BOLD);
   update_editable();
 
-  mvvline(3,2,0,MAX_CHANNELS+5);
-  mvvline(3,77,0,MAX_CHANNELS+5);
+  mvvline(3,2,0,MAX_OUPUT_CHANNELS+5);
+  mvvline(3,77,0,MAX_OUPUT_CHANNELS+5);
   mvhline(2,2,0,76);
   mvhline(7,2,0,76);
-  mvhline(8+MAX_CHANNELS,2,0,76);
+  mvhline(8+MAX_OUPUT_CHANNELS,2,0,76);
   mvaddch(2,2,ACS_ULCORNER);
   mvaddch(2,77,ACS_URCORNER);
-  mvaddch(8+MAX_CHANNELS,2,ACS_LLCORNER);
-  mvaddch(8+MAX_CHANNELS,77,ACS_LRCORNER);
+  mvaddch(8+MAX_OUPUT_CHANNELS,2,ACS_LLCORNER);
+  mvaddch(8+MAX_OUPUT_CHANNELS,77,ACS_LRCORNER);
 
   mvaddch(7,2,ACS_LTEE);
   mvaddch(7,77,ACS_RTEE);
@@ -1650,15 +1683,15 @@
   move(2,7);
   addstr(" output ");
 
-  mvhline(9+MAX_CHANNELS,0,0,80);
-  mvhline(18+MAX_CHANNELS,0,0,80);
+  mvhline(9+MAX_OUPUT_CHANNELS,0,0,80);
+  mvhline(18+MAX_OUPUT_CHANNELS,0,0,80);
 
   main_update_master(main_master_volume,5);
   main_update_playbuffer(4);
   main_update_outchannel_labels(7);
 
-  main_update_cues(10+MAX_CHANNELS);
-  main_update_tags(19+MAX_CHANNELS);
+  main_update_cues(10+MAX_OUPUT_CHANNELS);
+  main_update_tags(19+MAX_OUPUT_CHANNELS);
   curs_set(0);
 
   refresh();
@@ -1711,7 +1744,7 @@
         if(ch=='y'){
           unsaved=1;
           delete_cue_bank(cue_list_number);
-	  main_update_cues(10+MAX_CHANNELS);
+	  main_update_cues(10+MAX_OUPUT_CHANNELS);
         }
         move(0,0);
         addstr("MTG Beaverphonic build "VERSION": ");
@@ -1762,7 +1795,7 @@
         editable=1;
       update_editable();
     case 0:
-      main_update_tags(19+MAX_CHANNELS);
+      main_update_tags(19+MAX_OUPUT_CHANNELS);
       main_update_playbuffer(4);
       main_update_outchannel_labels(7);
       break;
@@ -1925,7 +1958,7 @@
   mvaddstr(10,2,"loop                      crosslap       ms");
   mvaddstr(11,2,"volume master        % fade       /      ms");
   
-  form_init(&f,7+MAX_CHANNELS*t->channels);
+  form_init(&f,7+MAX_OUPUT_CHANNELS*t->channels);
   strcpy(tdesc,label_text(t->sample_desc));
 
   field_add(&f,FORM_GENERIC,18,7,59,tdesc);
@@ -1953,13 +1986,13 @@
   addstr(buf);
 
   mvhline(13,3,0,74);
-  mvhline(14+MAX_CHANNELS,3,0,74);
-  mvvline(14,2,0,MAX_CHANNELS);
-  mvvline(14,77,0,MAX_CHANNELS);
+  mvhline(14+MAX_OUPUT_CHANNELS,3,0,74);
+  mvvline(14,2,0,MAX_OUPUT_CHANNELS);
+  mvvline(14,77,0,MAX_OUPUT_CHANNELS);
   mvaddch(13,2,ACS_ULCORNER);
   mvaddch(13,77,ACS_URCORNER);
-  mvaddch(14+MAX_CHANNELS,2,ACS_LLCORNER);
-  mvaddch(14+MAX_CHANNELS,77,ACS_LRCORNER);
+  mvaddch(14+MAX_OUPUT_CHANNELS,2,ACS_LLCORNER);
+  mvaddch(14+MAX_OUPUT_CHANNELS,77,ACS_LRCORNER);
   
   if(t->channels==2){
     mvaddstr(13,5," L ");
@@ -1972,15 +2005,15 @@
     }
   }
 
-  for(i=0;i<MAX_CHANNELS;i++){
-    for(j=0;j<t->channels && j<2;j++)
+  for(i=0;i<MAX_OUPUT_CHANNELS;i++){
+    for(j=0;j<t->channels && j<MAX_INPUT_CHANNELS;j++)
       field_add(&f,FORM_PERCENTAGE,4+j*5,14+i,5,&c->mix.outvol[j][i]);
     sprintf(buf,"%% ->%2d ",i);
     mvaddstr(14+i,4+t->channels*5,buf);
     addnlstr(channel_list[i].label,76-11-t->channels*5,' ');
   }
 
-  field_add(&f,FORM_BUTTON,61,17+MAX_CHANNELS,16,"ACCEPT CHANGES");
+  field_add(&f,FORM_BUTTON,61,17+MAX_OUPUT_CHANNELS,16,"ACCEPT CHANGES");
 
 
 #if 0
@@ -2046,7 +2079,7 @@
   
   mvaddstr(10,2,"volume master        % fade       ms");
   
-  form_init(&f,3+MAX_CHANNELS*t->channels);
+  form_init(&f,3+MAX_OUPUT_CHANNELS*t->channels);
   strcpy(tdesc,label_text(t->sample_desc));
 
   field_add(&f,FORM_PERCENTAGE,18,10,5,&c->mix.vol_master);
@@ -2069,13 +2102,13 @@
   addstr(buf);
 
   mvhline(12,3,0,74);
-  mvhline(13+MAX_CHANNELS,3,0,74);
-  mvvline(13,2,0,MAX_CHANNELS);
-  mvvline(13,77,0,MAX_CHANNELS);
+  mvhline(13+MAX_OUPUT_CHANNELS,3,0,74);
+  mvvline(13,2,0,MAX_OUPUT_CHANNELS);
+  mvvline(13,77,0,MAX_OUPUT_CHANNELS);
   mvaddch(12,2,ACS_ULCORNER);
   mvaddch(12,77,ACS_URCORNER);
-  mvaddch(13+MAX_CHANNELS,2,ACS_LLCORNER);
-  mvaddch(13+MAX_CHANNELS,77,ACS_LRCORNER);
+  mvaddch(13+MAX_OUPUT_CHANNELS,2,ACS_LLCORNER);
+  mvaddch(13+MAX_OUPUT_CHANNELS,77,ACS_LRCORNER);
   
   if(t->channels==2){
     mvaddstr(12,5," L ");
@@ -2088,15 +2121,15 @@
     }
   }
 
-  for(i=0;i<MAX_CHANNELS;i++){
-    for(j=0;j<t->channels && j<2;j++)
+  for(i=0;i<MAX_OUPUT_CHANNELS;i++){
+    for(j=0;j<t->channels && j<MAX_INPUT_CHANNELS;j++)
       field_add(&f,FORM_PERCENTAGE,4+j*5,13+i,5,&c->mix.outvol[j][i]);
     sprintf(buf,"%% ->%2d ",i);
     mvaddstr(13+i,4+t->channels*5,buf);
     addnlstr(channel_list[i].label,76-11-t->channels*5,' ');
   }
 
-  field_add(&f,FORM_BUTTON,61,16+MAX_CHANNELS,16,"ACCEPT CHANGES");
+  field_add(&f,FORM_BUTTON,61,16+MAX_OUPUT_CHANNELS,16,"ACCEPT CHANGES");
 
 
 #if 0
@@ -2444,7 +2477,6 @@
       menu=menu_output();
       break;
     case MENU_EDIT:
-      halt_playback();
       menu=edit_cue_menu();
       break;
     }

<p><p><p>--- >8 ----
List archives:  http://www.xiph.org/archives/
Ogg project homepage: http://www.xiph.org/ogg/
To unsubscribe from this list, send a message to 'cvs-request at xiph.org'
containing only the word 'unsubscribe' in the body.  No subject is needed.
Unsubscribe messages sent to the list will be ignored/filtered.



More information about the commits mailing list