iphone - CFReadStream - 在后台启动

标签 iphone ios core-audio core-foundation

有一个音频应用程序可以通过网络传输文件,一切正常,但有一件事。为了在后台自动播放下一首轨道,CFReadStream 在调用 AudioQueueStop 后被初始化(我可以在日志中看到它),但回调永远不会被调用(编辑:实际上被调用一次),直到应用程序进入前台。流初始化的代码段:

    //also tried main runloop just for test, no luck 
CFReadStreamScheduleWithRunLoop(stream, CFRunLoopGetCurrent(), kCFRunLoopCommonModes);

有线的事情是应用程序在队列停止后运行,流正在初始化,但只有当流在前台模式下初始化时才能正确调用回调。下面是一段回调代码:

    CFReadStreamSetClient(stream,
                      kCFStreamEventHasBytesAvailable | kCFStreamEventErrorOccurred | kCFStreamEventEndEncountered,
                      MyReadStreamCallBack,
                      &context);

另一方面,当应用程序位于后台时,回调会被调用,并且不会自动触发下一个轨道,而是通过应用程序委托(delegate)(具有相同的功能)触发。

我不完全理解这三种情况之间的区别,请帮忙。

编辑。

OSStatus status = AudioFileStreamOpen(self, MyAudioListener ...

正在调用 MyAudioListener 回调,同时调用 MyReadStreamCallBack 仅一次

编辑2

ReadStream 回调通常不会被调用一次,一次是我能看到的最大次数。

另一方面,这让我误解了正在发生的事情,在前一个音频队列停止并且下一个轨道是本地文件之后,然后>另一个AudioQueue被打开,它使用AudioFileReadPackets读取文件,我不必从后台唤醒应用程序来开始下一个轨道播放,因为它在后台播放本身。

最佳答案

如果有适当的后台模式,音频队列将继续在后台运行。但是一旦停止,音频队列似乎就不会开始在后台运行。一个回调可能只是为了准备缓冲区,以便队列可以在被带到前台后立即启动。

我发现的唯一解决方案是在后台时不停止以前的音频队列,而是以某种方式将新的音频数据提供给仍在运行的旧音频队列,而不会在其间发生任何回调下溢。

关于iphone - CFReadStream - 在后台启动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8966623/

相关文章:

iphone - iOS6 : do we have to set rootViewController in App delegate in order to support different orientations?

ios - 移动 View Controller 时出错

xcode - 苹果软件版本命名约定

objective-c - CAFAudioDescription 成员类型和字节顺序

iOS - 更新多任务栏中的媒体播放/暂停状态

objective-c - 如何在 Objective-C 中将 float 格式化为 2 位小数

ios - iphone nsoperation 应用程序卡住

ios - `inputProcRefCon` 中的 `AURenderCallbackStruct` 是什么?

ios - 为 Debug-iphoneos 构建时如何调试断言

ios - 如何在 spritekit 中使用 swift 转换场景