source: examples/utils.c @ dd15573

feature/autosinkfeature/cnnfeature/cnn_orgfeature/constantqfeature/crepefeature/crepe_orgfeature/pitchshiftfeature/pydocstringsfeature/timestretchfix/ffmpeg5pitchshiftsamplertimestretchyinfft+
Last change on this file since dd15573 was d795463, checked in by Paul Brossier <piem@piem.org>, 12 years ago

examples/utils.c: make -i optional

  • Property mode set to 100644
File size: 10.8 KB
Line 
1/*
2  Copyright (C) 2003-2009 Paul Brossier <piem@aubio.org>
3
4  This file is part of aubio.
5
6  aubio is free software: you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation, either version 3 of the License, or
9  (at your option) any later version.
10
11  aubio is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  GNU General Public License for more details.
15
16  You should have received a copy of the GNU General Public License
17  along with aubio.  If not, see <http://www.gnu.org/licenses/>.
18
19*/
20
21/**
22
23  This file includes some tools common to all examples. Code specific to the
24  algorithm performed by each program should go in the source file of that
25  program instead.
26
27*/
28
29#include "utils.h"
30
31#ifdef HAVE_LASH
32#include <lash/lash.h>
33#include <pthread.h>
34lash_client_t *aubio_lash_client;
35lash_args_t *lash_args;
36void *lash_thread_main (void *data);
37int lash_main (void);
38void save_data (void);
39void restore_data (lash_config_t * lash_config);
40pthread_t lash_thread;
41#endif /* HAVE_LASH */
42
43/* settings */
44const char *sink_uri = NULL;
45const char *source_uri = NULL;
46int frames = 0;
47int verbose = 0;
48int usejack = 0;
49int frames_delay = 0;
50
51
52char_t * pitch_unit = "default";
53char_t * pitch_mode = "default";
54
55/* energy,specdiff,hfc,complexdomain,phase */
56char_t * onset_mode = "default";
57smpl_t threshold = 0.0;         // leave unset, only set as asked
58smpl_t silence = -90.;
59uint_t buffer_size = 512;       //1024;
60uint_t overlap_size = 256;      //512;
61uint_t samplerate = 44100;
62
63aubio_source_t *this_source = NULL;
64aubio_sink_t *this_sink = NULL;
65
66fvec_t *ibuf;
67fvec_t *obuf;
68fvec_t *woodblock;
69
70/* badly redeclare some things */
71smpl_t threshold;
72smpl_t averaging;
73const char *prog_name;
74
75void flush_process (aubio_process_func_t process_func,
76    aubio_print_func_t print);
77
78void
79usage (FILE * stream, int exit_code)
80{
81  fprintf (stream, "usage: %s [ options ] \n", prog_name);
82  fprintf (stream,
83      "       -h      --help          Display this message.\n"
84      "       -v      --verbose       Be verbose.\n"
85      "       -j      --jack          Use Jack.\n"
86      "       -o      --output        Output type.\n"
87      "       -i      --input         Input type.\n"
88      "       -O      --onset         Select onset detection algorithm.\n"
89      "       -t      --threshold     Set onset detection threshold.\n"
90      "       -s      --silence       Select silence threshold.\n"
91      "       -p      --pitch         Select pitch detection algorithm.\n"
92      "       -B      --bufsize       Set buffer size.\n"
93      "       -H      --hopsize       Set hopsize.\n"
94      "       -a      --averaging     Use averaging.\n");
95  exit (exit_code);
96}
97
98int
99parse_args (int argc, char **argv)
100{
101  const char *options = "hvjo:i:O:t:s:p:B:H:a";
102  int next_option;
103  struct option long_options[] = {
104    {"help", 0, NULL, 'h'},
105    {"verbose", 0, NULL, 'v'},
106    {"jack", 0, NULL, 'j'},
107    {"output", 1, NULL, 'o'},
108    {"input", 1, NULL, 'i'},
109    {"onset", 1, NULL, 'O'},
110    {"threshold", 1, NULL, 't'},
111    {"silence", 1, NULL, 's'},
112    {"pitch", 1, NULL, 'p'},
113    {"averaging", 0, NULL, 'a'},
114    {"bufsize", 1, NULL, 'B'},
115    {"hopsize", 1, NULL, 'H'},
116    {NULL, 0, NULL, 0}
117  };
118#ifdef HAVE_LASH
119  lash_args = lash_extract_args (&argc, &argv);
120#endif /* HAVE_LASH */
121  prog_name = argv[0];
122  if (argc < 1) {
123    usage (stderr, 1);
124    return -1;
125  }
126  do {
127    next_option = getopt_long (argc, argv, options, long_options, NULL);
128    switch (next_option) {
129      case 'o':
130        sink_uri = optarg;
131        break;
132      case 'i':
133        source_uri = optarg;
134        break;
135      case 'h':                /* help */
136        usage (stdout, 0);
137        return -1;
138      case 'v':                /* verbose */
139        verbose = 1;
140        break;
141      case 'j':
142        usejack = 1;
143        break;
144      case 'O':                /*onset type */
145        onset_mode = optarg;
146        break;
147      case 's':                /* silence value for onset */
148        silence = (smpl_t) atof (optarg);
149        break;
150      case 't':                /* threshold value for onset */
151        threshold = (smpl_t) atof (optarg);
152        break;
153      case 'p':
154        pitch_mode = optarg;
155        break;
156      case 'a':
157        averaging = 1;
158        break;
159      case 'B':
160        buffer_size = atoi (optarg);
161        break;
162      case 'H':
163        overlap_size = atoi (optarg);
164        break;
165      case '?':                /* unknown options */
166        usage (stderr, 1);
167        break;
168      case -1:                 /* done with options */
169        break;
170      default:                 /*something else unexpected */
171        fprintf (stderr, "Error parsing option '%c'\n", next_option);
172        abort ();
173    }
174  }
175  while (next_option != -1);
176
177  if ( source_uri == NULL ) {
178    if (argc - optind == 1) {
179      source_uri = argv[optind];
180    } else if ( argc - optind > 1 ) {
181      errmsg ("Error: too many non-option arguments `%s'\n", argv[argc - 1]);
182      usage ( stderr, 1 );
183    }
184  } else if ( argc - optind > 0 ) {
185    errmsg ("Error: extra non-option argument %s\n", argv[optind]);
186    usage ( stderr, 1 );
187  }
188
189  if (source_uri != NULL) {
190    debug ("Input file : %s\n", source_uri);
191  } else if (source_uri != NULL && sink_uri != NULL) {
192    debug ("Input file : %s\n", source_uri);
193    debug ("Output file : %s\n", sink_uri);
194  } else {
195#if HAVE_JACK
196    debug ("Jack input output\n");
197    usejack = 1;
198#else
199    errmsg("Error: no arguments given (and no available audio input)\n");
200    usage ( stderr, 1 );
201#endif
202  }
203
204  return 0;
205}
206
207void
208examples_common_init (int argc, char **argv)
209{
210
211  /* parse command line arguments */
212  parse_args (argc, argv);
213
214  if (!usejack) {
215    debug ("Opening files ...\n");
216    this_source = new_aubio_source ((char_t*)source_uri, 0, overlap_size);
217    if (this_source == NULL) {
218      outmsg ("Could not open input file %s.\n", source_uri);
219      exit (1);
220    }
221    samplerate = aubio_source_get_samplerate(this_source);
222    if (sink_uri != NULL) {
223      this_sink = new_aubio_sink ((char_t*)sink_uri, samplerate);
224      if (this_sink == NULL) {
225        outmsg ("Could not open output file %s.\n", sink_uri);
226        exit (1);
227      }
228    }
229  }
230#ifdef HAVE_LASH
231  else {
232    aubio_lash_client = lash_init (lash_args, argv[0],
233        LASH_Config_Data_Set | LASH_Terminal, LASH_PROTOCOL (2, 0));
234    if (!aubio_lash_client) {
235      fprintf (stderr, "%s: could not initialise lash\n", __FUNCTION__);
236    }
237    /* tell the lash server our client id */
238    if (lash_enabled (aubio_lash_client)) {
239      lash_event_t *event =
240          (lash_event_t *) lash_event_new_with_type (LASH_Client_Name);
241      lash_event_set_string (event, "aubio");
242      lash_send_event (aubio_lash_client, event);
243      pthread_create (&lash_thread, NULL, lash_thread_main, NULL);
244    }
245  }
246#endif /* HAVE_LASH */
247
248  woodblock = new_fvec (overlap_size);
249  //TODO create woodblock sound
250
251  ibuf = new_fvec (overlap_size);
252  obuf = new_fvec (overlap_size);
253
254}
255
256void
257examples_common_del (void)
258{
259  del_fvec (ibuf);
260  del_fvec (obuf);
261  del_fvec (woodblock);
262  aubio_cleanup ();
263}
264
265#if HAVE_JACK
266aubio_jack_t *jack_setup;
267#endif
268
269void
270examples_common_process (aubio_process_func_t process_func,
271    aubio_print_func_t print)
272{
273
274  uint_t read = 0;
275  if (usejack) {
276
277#if HAVE_JACK
278    debug ("Jack init ...\n");
279    jack_setup = new_aubio_jack (1, 1,
280        0, 1, (aubio_process_func_t) process_func);
281    debug ("Jack activation ...\n");
282    aubio_jack_activate (jack_setup);
283    debug ("Processing (Ctrl+C to quit) ...\n");
284    pause ();
285    aubio_jack_close (jack_setup);
286#else
287    usage (stderr, 1);
288    outmsg ("Compiled without jack output, exiting.\n");
289#endif
290
291  } else {
292    /* phasevoc */
293    debug ("Processing ...\n");
294
295    frames = 0;
296
297    do {
298      aubio_source_do (this_source, ibuf, &read);
299      process_func (&ibuf->data, &obuf->data, overlap_size);
300      print ();
301      if (this_sink) {
302        aubio_sink_do (this_sink, obuf, overlap_size);
303      }
304      frames++;
305    } while (read == overlap_size);
306
307    debug ("Processed %d frames of %d samples.\n", frames, buffer_size);
308
309    flush_process (process_func, print);
310    del_aubio_source (this_source);
311    del_aubio_sink   (this_sink);
312
313  }
314}
315
316void
317flush_process (aubio_process_func_t process_func, aubio_print_func_t print)
318{
319  uint_t i;
320  fvec_zeros(obuf);
321  for (i = 0; (signed) i < frames_delay; i++) {
322    process_func (&ibuf->data, &obuf->data, overlap_size);
323    print ();
324  }
325}
326
327void
328send_noteon (int pitch, int velo)
329{
330  smpl_t mpitch = floor (aubio_freqtomidi (pitch) + .5);
331#if HAVE_JACK
332  jack_midi_event_t ev;
333  ev.size = 3;
334  ev.buffer = malloc (3 * sizeof (jack_midi_data_t)); // FIXME
335  ev.time = 0;
336  if (usejack) {
337    ev.buffer[2] = velo;
338    ev.buffer[1] = mpitch;
339    if (velo == 0) {
340      ev.buffer[0] = 0x80;      /* note off */
341    } else {
342      ev.buffer[0] = 0x90;      /* note on */
343    }
344    aubio_jack_midi_event_write (jack_setup, (jack_midi_event_t *) & ev);
345  } else
346#endif
347  if (!verbose) {
348    if (velo == 0) {
349      outmsg ("%f\n", frames * overlap_size / (float) samplerate);
350    } else {
351      outmsg ("%f\t%f\t", mpitch, frames * overlap_size / (float) samplerate);
352    }
353  }
354}
355
356
357#if HAVE_LASH
358
359void *
360lash_thread_main (void *data __attribute__ ((unused)))
361{
362  printf ("LASH thread running\n");
363
364  while (!lash_main ())
365    usleep (1000);
366
367  printf ("LASH thread finished\n");
368  return NULL;
369}
370
371int
372lash_main (void)
373{
374  lash_event_t *lash_event;
375  lash_config_t *lash_config;
376
377  while ((lash_event = lash_get_event (aubio_lash_client))) {
378    switch (lash_event_get_type (lash_event)) {
379      case LASH_Quit:
380        lash_event_destroy (lash_event);
381        exit (1);
382        return 1;
383      case LASH_Restore_Data_Set:
384        lash_send_event (aubio_lash_client, lash_event);
385        break;
386      case LASH_Save_Data_Set:
387        save_data ();
388        lash_send_event (aubio_lash_client, lash_event);
389        break;
390      case LASH_Server_Lost:
391        return 1;
392      default:
393        printf ("%s: received unknown LASH event of type %d",
394            __FUNCTION__, lash_event_get_type (lash_event));
395        lash_event_destroy (lash_event);
396        break;
397    }
398  }
399
400  while ((lash_config = lash_get_config (aubio_lash_client))) {
401    restore_data (lash_config);
402    lash_config_destroy (lash_config);
403  }
404
405  return 0;
406}
407
408void
409save_data ()
410{
411  lash_config_t *lash_config;
412
413  lash_config = lash_config_new_with_key ("threshold");
414  lash_config_set_value_double (lash_config, threshold);
415  lash_send_config (aubio_lash_client, lash_config);
416
417}
418
419void
420restore_data (lash_config_t * lash_config)
421{
422  const char *lash_key;
423
424  lash_key = lash_config_get_key (lash_config);
425
426  if (strcmp (lash_key, "threshold") == 0) {
427    threshold = lash_config_get_value_double (lash_config);
428    return;
429  }
430
431}
432
433#endif /* HAVE_LASH */
Note: See TracBrowser for help on using the repository browser.