AVAudioSession(2):定义一个 Audio Session
本文转自:AVAudioSession(2):定义一个 Audio Session | www.samirchen.com
本文内容主要来源于 Defining an Audio Session。
Audio Session 的默认行为
AVAudioSession 的默认行为如下:
- 音频播放能力是开启的,但是音频录制能力是关闭的。
- 当用户通过静音键切换到静音模式时,你的音频会被静音。
- 当用户通过锁屏键锁定屏幕或者自动锁屏定时触发时,你的音频会被静音。
- 当你的音频开始播放时,正在播放的其他 App 的音频会被静音。
这些行为是由默认的 AVAudioSessionCategorySoloAmbient Category 设定的。通常默认设置是不能满足你的需求的,除非你的 App 对音频的控制场景如下:
- 你的 App 只使用 System Sound Services 或者 UIKit 中的 playInputClick 方法来处理音频,而没有用到其他音频相关的 API 时。
- 你的 App 不使用任何音频。
系统如何解决竞争性的音频请求
流程大致如下图,还是挺好理解的:

需要注意的是,系统永远遵循一个原则:电话的优先级最高。
和 AVCaptureSession 协同
在 AV Foundatin capture 相关的 API 中(AVCaptureDevice, AVCaptureSession)允许你从摄像头和麦克风采集同步的音视频数据。其中表示麦克风的 AVCaptureDevice 对象可以共享你的 AVAudioSession。通常情况下,如果 AVCaptureSession 需要使用麦克风进行音频录制时,它会去修改优化你的 AVAudioSession 配置。如果你不希望这样,则需要设置对应的 AVCaptureSession 对象的 automaticallyConfiguresApplicationAudioSession 属性为 NO 来让 AVCaptureSession 使用你当前的 AVAudioSession 配置而不会修改它。
初始化 Audio Session
代码如下:
// implicitly initializes your audio session
AVAudioSession *session = [AVAudioSession sharedInstance];
音量和路径控制
苹果官方推荐使用 MPVolumeView 来控制音频音量和路径,MPVolumeView 提供了一个 Slider 来控制音量,提供了一个按钮来供你选择音频输出路径。
你可以通过如下代码来设置音频输出路径到话筒:
[[AVAudioSession sharedInstance] overrideOutputAudioPort:AVAudioSessionPortOverrideSpeaker error:nil];
但苹果推荐你用 MPVolumeView 提供的路径选择按钮来实现音频输出路径切换。
响应远程控制事件
通过响应 Remote Control Events 能让你在播放音视频内容时,可以响应来自锁屏界面、外部设备等 App 外部的控制。
具体参见 Remote Control Events 和 MPNowPlayingInfoCenter Class Reference。
激活和关闭 Audio Session
苹果官方建议如果你需要用到 Audio Session,总是应该显示地激活你的 Audio Session。并且参考 Setting Preferred Hardware Values 来设置相应的硬件参数。这样可以在你使用 Audio Session 前来测试是否能成功激活,以便于做出正确的处理逻辑。
激活 Audio Session 代码如下:
NSError *activationError = nil;
BOOL success = [[AVAudioSession sharedInstance] setActive:YES error:&activationError]; // Pass 'NO' when deactivate your audio session.
if (!success) { /* handle the error in activationError */ }
值得注意的是,大部分时候我们不需要关闭 Audio Session,除非是在 VoIP(Voice over Internet Protocol) 类应用、turn-by-turn 导航类应用和某些录制类应用中。这时你需要注意:
- 对于 VoIP 类应用,要确保 Audio Session 只在电话接听中是 Active 的。当应用处于后台时,保持应用为准备接听电话的状态,但应用的 Audio Session 应该是 Inactive 的。
- 对于定位于 Recording Category 来使用 Audio Session 的应用,要确保只在录制中设置 Audio Session 为 Active 状态,在录制开始前和录制结束后要确保 Audio Session 为 Inactive 状态以允许其他音频的播放。
检查是否有其他音频正在播放
你可以通过 otherAudioPlaying 来检查是否当前有其他应用的音频正在播放。
比如你是一个自带音效的游戏,当一个正在听音乐的用户打开你的游戏时,iOS 设计指南会建议你不要关闭用户正在听的音乐而播放你的游戏音效,这时候你怎么处理呢?你可以用上面的接口检查一下,如果有声音在播放则将你的音效静音并设置 AVAudioSessionCategorySoloAmbient。
Inter-App Audio 特性
Inter-App Audio 特性允许一个 Node App 将它的音频输出给一个 Host App。也可以由 Host App 发送它的音频给 Node App 进行处理,处理完后再发回给 Host App。Host App 需要设置一个 Active 的 Audio Session,而 Node App 则只在从 Host App 或系统接收音频输入时才需要一个 Active 的 Audio Session。
你可以使用下面这些规则来搭建 Inter-App Audio:
- 为 Node App 和 Host App 都设置 「inter-app-audio」的 entitlement。
- 为 Host App 设置 UIBackgroundModes 的 audio flag。
- 为那些在与 Host App 连接时使用音频输入或输出路径的 Node App 设置 UIBackgroundModes 的 audio flag。
- 为 Node App 和 Host App 都设置 AVAudioSessionCategoryOptionMixWithOthers 这个 Category。
- 确保连接着 inter-app host 的 Node App 在接收来自系统的音频或者输出音频时的 Audio Session 是 Active 的。
AVAudioSession(2):定义一个 Audio Session的更多相关文章
- AVAudioSession(3):定制 Audio Session 的 Category
本文转自:AVAudioSession(3):定制 Audio Session 的 Category | www.samirchen.com 本文内容主要来源于 Working with Catego ...
- AVAudioSession(1):iOS Audio Session 概览
本文转自:AVAudioSession(1):iOS Audio Session 概览 | www.samirchen.com 本文内容主要来源于 Audio Session Programming ...
- H5页面实现一个Audio标签加载多个音频文件,并进行播放和展示音频长度
最近微信项目中有需求,要将微信端发送过来的amr格式的语音文件,在项目中的页面上进行展示和播放,实现方式如下: 1.首先java后台收到微信端的消息推送的时候,使用 ffmpeg将amr格式的音频文件 ...
- audio session config
#pragma mark - #pragma mark - audio session config - (void)setAudioSessionConfig { NSError *error; A ...
- IOS Audio session
iOS实现长时间后台的两种方法:Audio session和VOIP socket 十二月 04 我们知道 iOS 开启后台任务后可以获得最多 600 秒的执行时间,而一些需要在后台下载或者与服务器保 ...
- NX二次开发-如何在类外面定义一个结构体
#include <uf.h> #include <uf_obj.h> #include <uf_part.h> using namespace NXOpen; u ...
- 用CIL写程序:定义一个叫“慕容小匹夫”的类
前文回顾: <用CIL写程序:你好,沃尔德> <用CIL写程序:写个函数做加法> 前言: 今天是乙未羊年的第一天,小匹夫先在这里给各位看官拜个年了.不知道各位看官是否和匹夫一样 ...
- java怎么定义一个二维数组?
java中使用 [][] 来定义二维数组 定义数组时也可同时初始化下面是一些例子float[][] numthree; //定义一个float类型的2维数组numthree=new float[5][ ...
- 将对象的所有属性名放到一个数组中 || 获得对象的所有属性名 || return;不具有原子性 || 怎样自己制作异常|| 判断对象有没有某个属性 || 当传递的参数比需要的参数少的时候,没有的值会被赋予undefined || 获得函数实际传递的参数 || 怎么用函数处理一个对象 || 用一个名字空间定义一个模块所有的函数 || 给一个对象添加方法
获得对象的所有属性名 || 将对象o的所有属性名放到数组中 var o = {x:1,y:2,z:3}; var arr = []; var i = 0; for(arr[i++] in o){};/ ...
随机推荐
- python3 selenium 如何处理异常情况
使用场景: 1.元素只有在某一特定情况下才会出现 2.元素定位不到 使用方法: try: except exceptions.NoSuchElementException: 举例说明: # _._ c ...
- druid抛出的异常------javax.management.InstanceAlreadyExistsException引发的一系列探索
最近项目中有个定时任务的需求,定时检查mysql数据与etcd数据的一致性,具体实现细节就不说了,今天要说的就是实现过程中遇到了druid抛出的异常,以及解决的过程 异常 异常详细信息 五月 05, ...
- Linux 按时间批量删除文件(删除N天前文件)
需要根据时间删除这个目录下的文件,/home/lifeccp/dicom/studies,清理掉20天之前的无效数据. 可以使用下面一条命令去完成: -name "*.*" -ex ...
- 查看当前用户名称:whoami命令
没什么可讲的,就是显示当前用户名称,效果同"id -un"命令.
- js函数的使用
js函数应用 [函数的声明及调用]: 1.函数声明: function 函数名(参数1,参数2,·····){ //函数体 retu ...
- [刷题]算法竞赛入门经典(第2版) 6-6/UVa12166 - Equilibrium Mobile
题意:二叉树代表使得平衡天平,修改最少值使之平衡. 代码:(Accepted,0.030s) //UVa12166 - Equilibrium Mobile //Accepted 0.030s //# ...
- 使用Nginx实现Tomcat集群负载均衡
概述 要解决的问题 环境准备以及问题解决思路 配置 测试 小结 一.概述 使用Nginx主要是来解决高并发情况下的负载均衡问题. 二.要解决的问题 1.最主要是负载均衡请求分发. 2.文件上传功能,只 ...
- 从C++ int类型的变量范围谈起
从学习C语言开始,int类型所占字节数,以及数值范围就是一个挥之不去的问题.一开始会死记硬背一个char 1个字节,一个字节8个bit.64位机器上面一个int 4个字节,32位机器上面不一样.那时候 ...
- Redis学习-SortedSet
Sorted-Sets和Sets类型极为相似,它们都是字符串的集合,都不允许重复的成员出现在一个Set中.它们之间的主要差别是Sorted-Sets中的每一个成员都会有一个分数(score)与之关联, ...
- SpringData系列三 Repository Bean 方法定义规范
本节主要介绍Repository Bean中方法定义规范. 1.方法不是随便声明,需要符合一定的规范. 2.按照Spring Data的规范,查询方法以find|read|get开头,涉及条件查询时, ...