激活音频会话
我们可以通过设置音频会话的类别、选项和模式来配置音频会话。要使配置生效,现在需要激活音频会话。
系统如何解决相互竞争的音频需求
随着APP的启动,手机内置的应用程序(消息、音乐、Safari、电话)可能正在后台运行。每一个都可能产生音频:比如一条短信的到达,10分钟前开始的播客继续播放,等等。
如果把一个设备想象成一个机场,把APP想象成一个滑行的飞机,那么这个系统就像一个控制塔。APP可以发出音频请求,并说明其所需的优先级,但对“停机坪上”发生的事情的最终权限由系统控制。
这时,APP就使用音频会话与“控制塔”,也就是系统,进行通信。整个流程如下:
- 首先我们的APP请求激活其音频会话。此时会向系统发起激活请求;
- 接下来,系统根据我们分配给音频会话的类别来考虑和判断是否需要激活请求。比如说,我们的APP使用一个要求其他音频被静音的类别。
- 此时,系统将停用其他程序的音频会话,停止其音频播放。
- 最后,系统将激活我们的的音频会话,并开始播放。
激活和停用音频会话
尽管AVFoundation的播放和录制类会自动激活音频会话,但手动激活它会让我们知道激活是否成功。同样,在更改音频会话的激活/停用状态时,可以检查是否更改成功,来对相应的处理系统拒绝激活会话的情况。
当有时钟、日历闹钟、来电时,系统会停用我们的音频会话。当用户解除警报或选择忽略电话呼叫时,系统允许会话再次激活。是否在中断结束时重新激活会话取决于应用程序自己。
要激活或者停用音频会话,可以调用setActive方法。
当使用AVFoundation对象(AVPlayer、AVAudioRecorder等)播放或录制音频时,系统会在中断结束时重新激活音频会话。但是,如果注册通知消息,并显式重新激活音频会话,则可以验证重新激活是否成功,并且可以更新应用的状态和用户界面。
许多APP不需要显式停用音频会话。但也有一些例外,如VoIP应用程序、逐圈导航应用程序,在某些情况下还包括播放和录制的应用程序。
- 确保VoIP类APP的音频会话(通常在后台运行)仅在处理呼叫时处于活动状态。在后台,准备接听电话时,VoIP应用程序的音频会话不应处于活动状态。
- 确保使用录制类别的APP的音频会话仅在录制时处于活动状态。在开始录制和停止录制之前,请确保会话处于非活动状态,以允许播放其他声音。
- 如果APP支持后台音频播放或录制,则在进入后台时,如果APP未在使用音频(或正在准备使用音频),请停用其音频会话。这样做可以让系统释放音频资源,以便它们可以被其他进程使用。
检查是否正在播放其他音频
当APP激活时,设备上可能已经在播放声音。例如,当用户启动APP时,音乐APP可能正在播放歌曲,或者Safari可能正在播放音频流。如果我们的APP是一个游戏,知道是否有其他音频正在播放尤其重要。因为许多游戏都有音乐音轨和音效。iOS人机界面中的音频指南建议我们假设用户在玩游戏时希望其他音频和游戏的声音效果一起继续。
在APP的delegate的applicationDidBecomeActive:
方法中,检查音频会话的secondaryAudioShouldBeSilencedHint
属性以确定音频是否已在播放。当另一个具有非混合类别音频会话的APP正在播放音频时,该值为true。应用程序应使用此属性作为提示,以使应用程序运行时次要的音频静音。
我们还可以订阅AVAudioSessionSilenceSecondaryAudioHintNotification
类型的通知,以便那些可选的辅助音频静音开始或结束时通知我们来进行相应的处理。这个通知,只会发送给当前处于前台,并且是激活状态的音频会话的观察者。
这个通知在 userInfo 字典中的key为AVAudioSessionSilenceSecondaryAudioHintTypeKey
,值为AVAudioSessionSilenceSecondaryAudioHintType
类型。使用这个音频提示类型,来确定辅助音频静音应该开始还是结束。
网友评论