使用paContinue()函数实现音频流的连续播放
发布时间:2023-12-17 10:12:33
paContinue()函数是PortAudio库中的一个函数,用于指示回调函数继续读取音频数据进行播放。下面是使用paContinue()函数实现音频流的连续播放的一个例子。
#include <stdio.h>
#include "portaudio.h"
#define SAMPLE_RATE (44100)
#define FRAMES_PER_BUFFER (1024)
#define NUM_SECONDS (5)
typedef struct {
float *data;
int frameIndex;
int maxFrameIndex;
} AudioData;
AudioData audioData;
int audioCallback(const void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer,
const PaStreamCallbackTimeInfo *timeInfo,
PaStreamCallbackFlags statusFlags, void *userData) {
float *out = (float *)outputBuffer;
AudioData *data = (AudioData *)userData;
int framesLeft = data->maxFrameIndex - data->frameIndex;
if (framesLeft < framesPerBuffer) {
// If there are not enough frames left, fill the buffer with silence
memset(out, 0, sizeof(float) * framesPerBuffer);
return paComplete;
} else {
// Fill the buffer with audio data
memcpy(out, &(data->data[data->frameIndex]), sizeof(float) * framesPerBuffer);
data->frameIndex += framesPerBuffer;
return paContinue;
}
}
int main(void) {
PaStream *stream;
PaError err;
// Initialize PortAudio
err = Pa_Initialize();
if (err != paNoError) {
printf("Failed to initialize PortAudio: %s
", Pa_GetErrorText(err));
return 1;
}
// Initialize audio data
audioData.data = (float *)malloc(sizeof(float) * SAMPLE_RATE * NUM_SECONDS);
audioData.frameIndex = 0;
audioData.maxFrameIndex = SAMPLE_RATE * NUM_SECONDS;
// Fill audio data with some waveform
for (int i = 0; i < audioData.maxFrameIndex; i++) {
audioData.data[i] = (float)sin(2 * M_PI * 440 / SAMPLE_RATE * i);
}
// Open the stream
err = Pa_OpenDefaultStream(&stream, 0, 1, paFloat32, SAMPLE_RATE, FRAMES_PER_BUFFER,
audioCallback, &audioData);
if (err != paNoError) {
printf("Failed to open stream: %s
", Pa_GetErrorText(err));
return 1;
}
// Start the stream
err = Pa_StartStream(stream);
if (err != paNoError) {
printf("Failed to start stream: %s
", Pa_GetErrorText(err));
return 1;
}
// Wait for the stream to finish
Pa_Sleep(NUM_SECONDS * 1000);
// Stop and close the stream
err = Pa_StopStream(stream);
if (err != paNoError) {
printf("Failed to stop stream: %s
", Pa_GetErrorText(err));
return 1;
}
err = Pa_CloseStream(stream);
if (err != paNoError) {
printf("Failed to close stream: %s
", Pa_GetErrorText(err));
return 1;
}
// Terminate PortAudio
err = Pa_Terminate();
if (err != paNoError) {
printf("Failed to terminate PortAudio: %s
", Pa_GetErrorText(err));
return 1;
}
free(audioData.data);
return 0;
}
以上代码演示了使用paContinue()函数实现音频流的连续播放。代码首先通过Pa_Initialize()函数初始化了PortAudio库。然后创建了一个结构体AudioData,用于存储音频数据和相关参数。回调函数audioCallback()中,根据还剩下的音频帧数决定是填充音频数据还是填充静音。在main()函数中,通过Pa_OpenDefaultStream()函数打开音频流。使用Pa_StartStream()函数启动音频流的播放。通过Pa_Sleep()函数让程序等待一段时间,然后调用Pa_StopStream()函数停止音频流的播放,并通过Pa_CloseStream()函数关闭音频流。最后通过Pa_Terminate()函数终止PortAudio库的使用。
这个例子会播放一个长度为5秒的纯音频波形,示例中使用了sin函数生成了一个440Hz的正弦波。
