我正在为iPhone编写远程桌面客户端,我试图实现音频重定向。
客户端通过套接字连接连接到服务器,并且服务器一次发送32K大小的PCM数据块。使用音频队列服务通过套接字连接播放PCM数据
我想使用AQS来播放数据,它播放的前两秒(1缓冲区值)。但是,由于下一个数据块尚未通过套接字进入,下一个AudioQueueBuffer是空的。当数据进入时,我用数据填充下一个可用缓冲区,并使用AudioQueueEnqueueBuffer将其排入队列。但是,它从不播放这些缓冲区。
如果队列中没有缓冲区,即使稍后添加缓冲区,队列是否会停止播放?
下面的代码的相关部分:
void
wave_out_write(STREAM s, uint16 tick, uint8 index)
{
if(items_in_queue == NUM_BUFFERS){
return;
}
if(!playState.busy){
OSStatus status;
status = AudioQueueNewOutput(&playState.dataFormat, AudioOutputCallback, &playState, CFRunLoopGetCurrent(), NULL, 0, &playState.queue);
if(status == 0){
for(int i=0; i<NUM_BUFFERS; i++){
AudioQueueAllocateBuffer(playState.queue, 40000, &playState.buffers[i]);
}
AudioQueueAddPropertyListener(playState.queue, kAudioQueueProperty_IsRunning, MyAudioQueuePropertyListenerProc, &playState);
status = AudioQueueStart(playState.queue, NULL);
if(status ==0){
playState.busy = True;
}
else{
return;
}
}
else{
return;
}
}
playState.buffers[queue_hi]->mAudioDataByteSize = s->size;
memcpy(playState.buffers[queue_hi]->mAudioData, s->data, s->size);
AudioQueueEnqueueBuffer(playState.queue, playState.buffers[queue_hi], 0, 0);
queue_hi++;
queue_hi = queue_hi % NUM_BUFFERS;
items_in_queue++;
}
void AudioOutputCallback(void* inUserData, AudioQueueRef outAQ, AudioQueueBufferRef outBuffer)
{
PlayState *playState = (PlayState *)inUserData;
items_in_queue--;
}
谢谢!
你不必填充任何沉默。如果在调用回调函数时没有任何数据返回队列,则不要在其中放入任何数据。如果您的队列中的数据用完了,它将自行播放静默,直到您再次排列数据。如果所有缓冲区都不在队列中,则不会再次调用回调,但仍可以将数据从不是回调的另一个函数(例如,一旦数据再次到达)排入队列。这不是海报的问题。他的问题是他在队列中只有一个缓冲区开始。您至少需要2. – Mecki 2010-05-10 22:39:23
谢谢Mecki,我有类似的问题,即使解决方案尚未写入,至少这指向了正确的方向...... – Nick 2010-07-22 18:18:18