Jcapture

De wikijoan
Salta a la navegació Salta a la cerca

Introducció

Es tracta de l'aplicació mínima per tal de mostrar la informació que arriba del micròfon. Es dibuixa el senyal en forma d'un meter textual.

Desenvolupament

El rovell de l'ou està en la funció callback. Per cada crida de la funció callback n'hi hauria prou de copiar el buffer d'entrada (la senyal que ve del micro i que està disponible en la interfície d'audio) al fitxer de so mitjançant la funcion sf_write_float de la llibreria de libsndfile.

Ara bé, tot i que no faig processament del senyal (no canvio el valor de les mostres), m'interessa recórrer totes les mostres per tal d'obtenir un valor mitja de les mostres durant un periode de temps (calculat al llarg de 5 crides a la funció callback), i per tant implemento també el bucle for.

He perdut bastant de temps perquè utilitzava la funció ''sf_write_double en comptes de la correcte sf_write_float, i les mostres que obtenia quedaven molt reduïdes...

versions

  • 0.0.1: mostro per pantalla el valor de les mostres
  • 0.0.2: implemento un meter (mal calculat per culpa de la funció abs, veure més avall)
  • 0.0.3: incloc la llibreria libsndfile per escriure a un fitxer wav.
  • 1.0.0: versió definitiva. Es passa com a argument el nom del fitxer de sortida.

Problema amb el valor absolut

He perdut bastant de temps a l'hora de mostrar el meter textual, perquè la funció abs() no funcionava com s'espera. A A <cstdlib> està definida la funció abs0:

int abs ( int n );
long abs ( long n );

i com es veu només espera com a argument tipus enter. Com es llegeix en la documentació (http://www.cplusplus.com/reference/clibrary/cstdlib/abs/):

In C++, this function is overloaded in <cmath> for floating-point types (see cmath abs), in <complex> for complex numbers (see complex abs), and in <valarray> for valarrays (see valarray abs).

i per tant, si vull el valor absolut de valors float, he d'utilitzar la llibreria #include <cmath>. El codi mínim per veure el problema és (comentar o descomentar #include <cmath>):

using namespace std;
#include <stdio.h>
#include <stdlib.h>
#include <cmath>

int main (int argc, char* argv[]) 
{
	float a=.342;
	float b;
	b=(float)abs(a);
	printf("%f\n",b);

	return 0 ;
}

Realtime safe

printf no és realtime safe.

D'altra banda, jo a cada crida de la callback també faig

sf_write_float (sndfile, (float *)ins , nframes) ;	

i no crec que fer això dins de la callback sigui realtime safe. Per tant, la única alternativa serà fer-ho amb threads, com de fet ja està resolt a:

Download

Blog


creat per Joan Quintana Compte, febrer 2012