I'm currently building an mp3 streamer/receiver with the use of live555, mpg123 and portaudio, and just starting the concepts of streaming, decoding and playing mp3.
My problem is when I need to play the sound with portaudio. I can't figure how to write a callback function that will play my decoded mp3.
Here's the callback function that I found somewhere and tried, but that isn't giving me good results (nothing but noises and buzz).
static int patestCallback( const void *inputBuffer, void *outputBuffer,
unsigned long framesPerBuffer,
const PaStreamCallbackTimeInfo* timeInfo,
PaStreamCallbackFlags statusFlags,
void *userData )
{
/* Cast data passed through stream to our structure. */
paTestData *data_struct = (paTestData*)userData;
float *out = (float*)outputBuffer;
unsigned int i;
(void) inputBuffer; /* Prevent unused variable warning. */
for( i=0; i<framesPerBuffer; i++ )
{
if(data_struct->cursor < data_struct->num_frames)
{
out[i] = data_struct->data[data_struct->cursor];
data_struct->cursor++;
}
else
{
out[i] = 0; // if you've used up all the data, just fill the rest with silence.
//finished = paComplete;
}
}
return 0;
}
The callback function receives a struct containing the decoded data in an unsigned char array and the number of bytes decoded:
typedef struct
{
unsigned char* data;
unsigned long cursor;
unsigned long num_frames;
}
paTestData;
The codec function looks like this:
mpg123_decode(m,fBuffer,frameSize,out,OUTBUFF,&size);
So it returns the data in an unsigned char (out), with the bytes decoded in the size variable. fBuffer is the encoded data and frameSize the number of bytes encoded.
I've configured the portaudio stream the same way as in the portaudio tutorials:
err = Pa_OpenDefaultStream( &stream,
0, /* no input channels */
2, /* stereo output */
paFloat32, /* 32 bit floating point output */
SAMPLE_RATE,
paFramesPerBufferUnspecified, /* frames per buffer, i.e. the number
of sample frames that PortAudio will
request from the callback. Many apps
may want to use
paFramesPerBufferUnspecified, which
tells PortAudio to pick the best,
possibly changing, buffer size.*/
patestCallback, /* this is your callback function */
&paData ); /*This is a pointer that will be passed to
your callback*/
An example of a good callback function would be very useful, but of course any help is appreciated,
Thanks