~ubuntu-branches/ubuntu/karmic/mhwaveedit/karmic

« back to all changes in this revision

Viewing changes to src/soxdialog.c

  • Committer: Bazaar Package Importer
  • Author(s): Free Ekanayaka
  • Date: 2008-01-08 22:20:37 UTC
  • mfrom: (2.1.6 hardy)
  • Revision ID: james.westby@ubuntu.com-20080108222037-tsazhckl5vmc8yih
Tags: 1.4.14-2
Added desktop file (Closes: #457849), thanks to Marco Rodrigues

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
 
 * Copyright (C) 2003 2004 2005, Magnus Hjorth
 
2
 * Copyright (C) 2003 2004 2005 2006, Magnus Hjorth
3
3
 *
4
4
 * This file is part of mhWaveEdit.
5
5
 *
49
49
static gboolean sox_support_map[22] = { FALSE };
50
50
 
51
51
static gchar *supported_effect_names[] = { 
52
 
     N_("[S] Echo"),
53
 
     N_("[S] Echo sequence"),
54
 
     N_("[S] Reverb"),
55
 
     N_("[S] Chorus"),
56
 
     N_("[S] Flanger"),
57
 
     N_("[S] Phaser"),
58
 
     N_("[S] Compress/Expand"),
59
 
     N_("[S] Pitch adjust"),
60
 
     N_("[S] Time stretch"),
61
 
     N_("[S] DC Shift"),
62
 
     N_("[S] Masking noise"),
63
 
     N_("[S] Reverse"),
64
 
     N_("[S] Earwax"),
65
 
     N_("[S] Vibro"),
66
 
     N_("[S] Lowpass filter (single-pole)"),
67
 
     N_("[S] Highpass filter (single-pole)"),
68
 
     N_("[S] Bandpass filter"),
69
 
     N_("[S] Butterworth lowpass filter"),
70
 
     N_("[S] Butterworth highpass filter"),
71
 
     N_("[S] Butterworth bandpass filter"),
72
 
     N_("[S] Butterworth bandreject filter"),
73
 
     N_("[S] Sinc-windowed filter"),
 
52
     N_("Echo"),
 
53
     N_("Echo sequence"),
 
54
     N_("Reverb"),
 
55
     N_("Chorus"),
 
56
     N_("Flanger"),
 
57
     N_("Phaser"),
 
58
     N_("Compress/Expand"),
 
59
     N_("Pitch adjust"),
 
60
     N_("Time stretch"),
 
61
     N_("DC Shift"),
 
62
     N_("Masking noise"),
 
63
     N_("Reverse"),
 
64
     N_("Earwax"),
 
65
     N_("Vibro"),
 
66
     N_("Lowpass filter (single-pole)"),
 
67
     N_("Highpass filter (single-pole)"),
 
68
     N_("Bandpass filter"),
 
69
     N_("Butterworth lowpass filter"),
 
70
     N_("Butterworth highpass filter"),
 
71
     N_("Butterworth bandpass filter"),
 
72
     N_("Butterworth bandreject filter"),
 
73
     N_("Sinc-windowed filter"),
74
74
     NULL 
75
75
};
76
76
 
78
78
 
79
79
#define COMPAND_LINES 6
80
80
 
81
 
void sox_dialog_format_string(gchar *buf, guint bufsize, guint samplerate,
82
 
                              gboolean sign, guint samplesize, guint channels)
 
81
void sox_dialog_format_string(gchar *buf, guint bufsize, Dataformat *fmt)
83
82
{
84
 
     g_snprintf(buf,bufsize,"-t raw -r %d %s %s -c %d",samplerate,
85
 
                sign?"-s":"-u",samplesize_switch[samplesize],channels);
86
 
                
 
83
     g_assert(fmt->type == DATAFORMAT_PCM && fmt->samplesize != 3);
 
84
 
 
85
     g_snprintf(buf,bufsize,"-t raw -r %d %s %s -c %d",fmt->samplerate,
 
86
                fmt->sign?"-s":"-u",samplesize_switch[fmt->samplesize],
 
87
                fmt->channels);
87
88
}
88
89
 
89
 
static Chunk *sox_dialog_apply_proc(Chunk *chunk, StatusBar *bar, 
90
 
                                    gpointer user_data)
 
90
static Chunk *sox_dialog_apply_proc_main(Chunk *chunk, StatusBar *bar, 
 
91
                                         gpointer user_data)
91
92
{
92
93
     SoxDialog *sd = SOX_DIALOG(user_data);
93
94
     EffectDialog *ed = &(sd->ed);
98
99
     guint i,j;
99
100
     gint idx;
100
101
     gboolean b;
 
102
     off_t clipcount = 0;
 
103
     Chunk *r;
101
104
 
102
 
     sox_dialog_format_string(fmt_buf,sizeof(fmt_buf),chunk->format.samplerate,
103
 
                              chunk->format.sign,chunk->format.samplesize,
104
 
                              chunk->format.channels);
 
105
     sox_dialog_format_string(fmt_buf,sizeof(fmt_buf),&(chunk->format));
105
106
     g_snprintf(cmd_buf,sizeof(cmd_buf),"sox %s - %s - ",fmt_buf,fmt_buf);
106
 
                
 
107
     
107
108
     c=strchr(cmd_buf,0);     
108
109
     if (!strcmp(ed->effect_name,"echo") || 
109
110
         !strcmp(ed->effect_name,"echos") ||
232
233
     } else {
233
234
          g_assert_not_reached();
234
235
     }
235
 
     return pipe_dialog_pipe_chunk(chunk,cmd_buf,FALSE,dither_editing,bar);
 
236
     r = pipe_dialog_pipe_chunk(chunk,cmd_buf,FALSE,dither_editing,bar,
 
237
                                &clipcount);
 
238
     if (r != NULL && clipwarn(clipcount,TRUE)) {
 
239
          gtk_object_sink(GTK_OBJECT(r));
 
240
          return NULL;
 
241
     }
 
242
     return r;
 
243
}
 
244
 
 
245
static Chunk *sox_dialog_apply_proc(Chunk *chunk, StatusBar *bar, 
 
246
                                    gpointer user_data)
 
247
{
 
248
     Chunk *c,*d,*r;
 
249
     Dataformat stype = { DATAFORMAT_PCM, 44100, 4, 1, 4, TRUE, IS_BIGENDIAN };
 
250
     if ((chunk->format.type == DATAFORMAT_FLOAT) || 
 
251
         (chunk->format.type == DATAFORMAT_PCM && 
 
252
          chunk->format.samplesize == 3)) {
 
253
          c = chunk_convert_sampletype(chunk,&stype);
 
254
          d = sox_dialog_apply_proc_main(c,bar,user_data);
 
255
          gtk_object_sink(GTK_OBJECT(c));
 
256
          r = chunk_convert_sampletype(d,&(chunk->format));
 
257
          gtk_object_sink(GTK_OBJECT(d));
 
258
          return r;
 
259
     } else
 
260
          return sox_dialog_apply_proc_main(chunk,bar,user_data);
236
261
}
237
262
 
238
263
static gboolean sox_dialog_apply(EffectDialog *ed)
239
264
{
240
265
     SoxDialog *sd = SOX_DIALOG(ed);
241
266
     Document *d = EFFECT_BROWSER(ed->eb)->dl->selected;
242
 
     Chunk *chunk = d->chunk;
 
267
     /* Chunk *chunk = d->chunk; */
243
268
     guint i,j;
 
269
     /*
244
270
     if (chunk->format.samplesize != 1 &&
245
271
         chunk->format.samplesize != 2 &&
246
272
         chunk->format.samplesize != 4) {
247
273
          user_info(_("SoX only supports 8, 16 and 32-bit sample sizes"));
248
274
          return TRUE;
249
275
     }
 
276
     */
250
277
     if ((sd->fb1!=NULL && floatbox_check(sd->fb1)) ||
251
278
         (sd->fb2!=NULL && floatbox_check(sd->fb2)) || 
252
279
         (sd->fb3!=NULL && floatbox_check(sd->fb3)) || 
665
692
     return id;
666
693
}
667
694
 
668
 
gboolean sox_dialog_register_main(void)
 
695
gboolean sox_dialog_register_main(gchar source_tag)
669
696
{
670
 
     int fd[2],i,lb_pos=0;
 
697
     int fd[2],fd2[2],i,j,lb_pos=0;
671
698
     pid_t p;
672
699
     gchar *c,*d,**s,**sn;
673
 
     gchar linebuf[1024];
 
700
     gchar linebuf[4096];
674
701
     gboolean *map;
 
702
 
 
703
     if (!program_exists("sox")) return FALSE;
 
704
 
675
705
     /* Run the command 'sox -h' and try to see which effects it
676
706
      * supports. */
677
707
     i = pipe(fd);
678
 
     if (i == -1) {
 
708
     j = pipe(fd2);
 
709
     if (i == -1 || j == -1) {
679
710
          console_perror(_("Error creating pipe"));
 
711
          if (i == 0) { close(fd[0]); close(fd[1]); }
 
712
          if (j == 0) { close(fd2[0]); close(fd2[1]); }
680
713
          return TRUE;
681
714
     }
682
715
     p = fork();
683
716
     if (p == -1) {
684
717
          console_perror(_("Couldn't fork"));
 
718
          close(fd[0]);
 
719
          close(fd[1]);
 
720
          close(fd2[0]);
 
721
          close(fd2[1]);
685
722
          return TRUE;
686
723
     }
687
724
     if (p == 0) {
688
 
          /* Child process - run 'sox -h' and catch stderr output */
689
 
          close_all_files_except(&(fd[1]),1);
690
 
          if (dup2(fd[1],2)==-1 || execlp("sox","sox","-h",NULL)==-1)
 
725
          /* Child process - run 'sox -h' and catch stdout/stderr output */
 
726
          /* Put stdout descriptor in fd[0] */
 
727
          fd[0] = fd2[1];
 
728
          close_all_files_except(fd,2);
 
729
          if (dup2(fd[0],1)==-1 || dup2(fd[1],2)==-1 || 
 
730
              execlp("sox","sox","-h",NULL)==-1)
691
731
               
692
732
               printf(_("Error running 'sox -h': %s\n"),strerror(errno));
693
733
          else 
696
736
     } else {
697
737
          /* Parent process - read data */
698
738
          close(fd[1]);
699
 
          while (lb_pos < sizeof(linebuf)-1) {
700
 
               i = read(fd[0],linebuf+lb_pos,sizeof(linebuf)-lb_pos-1);
701
 
               if (i == 0) break;
 
739
          close(fd2[1]);
 
740
          /* Put stdout descriptor in fd array */
 
741
          fd[1] = fd2[0];
 
742
          /* Read input */
 
743
          j = 0;
 
744
          while (lb_pos < sizeof(linebuf)-1 && j<2) {
 
745
               i = read(fd[j],linebuf+lb_pos,sizeof(linebuf)-lb_pos-1);
 
746
               if (i == 0) j++; /* Read from other descriptor */
702
747
               if (i < 0) {
703
748
                    if (errno == EINTR) continue;
704
749
                    console_perror(_("Error reading sox output"));
712
757
          /* Scan for available effects */
713
758
          c = strstr(linebuf,"effect: ");
714
759
          if (c == NULL) {
715
 
               console_message(_("Unable to detect supported SoX effects"));
716
 
               return TRUE;
717
 
          }
718
 
          c += 8;
 
760
               c = strstr(linebuf,"effects: ");
 
761
               if (c == NULL) {
 
762
                    c = strstr(linebuf,"SUPPORTED EFFECTS: ");
 
763
                    if (c == NULL) {
 
764
                          console_message(_("Unable to detect supported "
 
765
                                              "SoX effects"));
 
766
                    return TRUE;
 
767
                    } else
 
768
                    c += 19;
 
769
                } else
 
770
                c += 9; 
 
771
          } else
 
772
            c += 8;
 
773
 
719
774
          d = strchr(c,'\n');
720
775
          if (d) *d=0;
721
776
          for (d=strtok(c," "); d!=NULL; d=strtok(NULL," ")) {
732
787
               for (s=supported_effects,sn=supported_effect_names,
733
788
                         map=sox_support_map; *s!=NULL; s++,sn++,map++)
734
789
                    if (*map) 
735
 
                         effect_browser_register_effect(*s,_(*sn),
736
 
                                                        sox_dialog_get_type());
 
790
                         effect_register_add_effect(source_tag,*s,_(*sn),
 
791
                                                    "Chris Bagwell","");
737
792
          return FALSE;
738
793
     }
739
794
     return FALSE;
740
795
}
741
796
 
 
797
void sox_dialog_rebuild_func(gchar source_tag, gpointer user_data)
 
798
{
 
799
     if (sox_dialog_register_main(source_tag)) 
 
800
          console_message(_("Sox support couldn't be initialized"));
 
801
}
 
802
 
 
803
EffectDialog *sox_dialog_get_func(gchar *name, gchar source_tag, 
 
804
                                  gpointer user_data)
 
805
{
 
806
     char **c;
 
807
     gboolean *b;
 
808
     for (c=supported_effects,b=sox_support_map; *c!=NULL; c++,b++) {
 
809
          if (*b && !strcmp(*c,name)) 
 
810
               return gtk_type_new(sox_dialog_get_type());
 
811
     }
 
812
     return NULL;
 
813
}
 
814
 
742
815
void sox_dialog_register(void)
743
816
{
744
 
     if (sox_dialog_register_main()) 
745
 
          console_message(_("Sox support couldn't be initialized"));
 
817
     effect_register_add_source("SoX",'S',sox_dialog_rebuild_func,NULL,
 
818
                                sox_dialog_get_func,NULL);
746
819
}
747
820
 
748
821
gchar *sox_dialog_first_effect(void)