安卓音频简析

Android音频分析

1        安卓音频系统框架

 技术分享技术分享


?  Multimedia framework:

多媒体框架负责封装了播放/录音类、连接安卓音频解码库进行音频软件解码以及连接高通OpenMaxIL接口。上层APP直接调用Multimedia framework的接口来进行音频的播放和录音。

 

?  AudioService

注册安卓广播事件,获取广播事件,如蓝牙耳机插拔、USB音频设备插拔等,并调用Audio System接口来实现音频控制。

 

?  AudioSystem

该类中包含了音频的基础定义,包括音频流(stream)类型,路由(Routing)类型、音频输入输出设备(device)的定义、音频设备声明(device states)以及一些音频接口函数。

 

?  Audio Flinger(AF):

AudioFlinger是安卓音频的两大服务之一,另一个是AudioPolicyService,这两个服务均由mediaserver实例化(main_mediaserver.cpp。AudioFlinger直接与HAL层通讯,所有的音频操作都需要经过AudioFlinger来控制。主要有以下功能:

1.      通过libaudio库的接口来管理所有的音频输入/输出设备;

2.      实现PCM数据的混音/输入/输出;

3.      播放时音量控制

 

?  Audio Policy Manager(APM):

APM主要用于音频流的路由策略,以及用户场景的切换,最终也是和AF通讯,有AF与HAL通讯控制。AudioPolicyService.java 也会通过AudioSystem中的接口(如AudioSystem::get_audio_flinger())来获取AF实例,音量的控制也是调用AudioSystem中的接口(如AudioSystem::setVoiceVolume(data->mVolume))来控制,最终AS也是调用AF的接口来实现。

 

?  AudioTrack(AT):

用于播放音频的类,通过audio_track_cblk_t AF共享内存,传递音频数据。

 

?  AudioRecord:

用于录音的类。

 

2        具体分析

2.1  AudioTrack(AT)分析

 

java层:frameworks\base\media\java\android\media\ AudioTrack.java

JNI层: frameworks\base\core\jni\android_media_AudioTrack.cpp

库:frameworks\av\media\libmedia\AudioTrack.cpp

三个文件的关系:java层AudioTrack.java调用JNI层android_media_AudioTrack.cppnative函数,JNI层具体功能再调用库AudioTrack.cpp中函数来实现。

s

总的来说,audiotrack.java提供给APP用于播放音频的类,通过JNI与c++文件通信完成具体的播放功能。

audiotrack.java主要提供以下几个方法:

getMinBufferSize():根据采样率,声道数,采样位数(采样精度)(分别对应三个形参)来计算需要的最小buffer缓冲区。

AudioTrack():构造函数,构造一个播放类;

paly():开始播放音频;

write():往AudioTrack中写入音频数据;

stop():停止播放;

pause():暂停播放;

release():释放底层的资源。

 

 

AudioTrack播放音频数据时有两种方式,一种是静态模式(MODE_STATIC),另一种是流模式(MODE_STREAM)。

? static

静态模式就是数据一次性交付给接收方。好处是简单高效,只需要进行一次操作就完成了数据的传递;缺点当然也很明显,无法胜任数据量较大的音频回放,因而通常只用于播放铃声、系统提醒等对内存小的操作。

? streaming

流模式和网络上播放视频是类似的,即数据是按照一定规律不断地传递给接收方的。理论上它可用于任何音频播放的场景,不过我们一般在以下情况下采用:

? 音频文件过大

? 音频属性要求高,比如采样率高、深度大的数据

? 音频数据是实时产生的,这种情况就只能用流模式了

 

 

AudioTrack的构造函数中有一个变量用来指定buffer的大小bufferSizeInBytes。

AudioTrack在Native层会对这个变量的值进行有效性判断。首先,它至少要等于或者大于getMinBufferSize返回的值,然后它必须是frame大小的整数倍。(frame=声道数*采样位数/8

举例说明,MODE_STREAM模式下,在JAVA层构造AudioTrack时,bufferSizeInBytes的大小设定为9600,在Native层调用Write方法拷贝数据至Hardware进行回放,每次拷贝的大小为320.则需要拷贝到30次,声卡才发出声音。即需要将数据填满缓冲区才进行播放。(320*30=9600)

 

See also:

Android深入浅出之Audio 第一部分 AudioTrack分析

http://blog.csdn.net/onetwothreef/article/details/46311985

深入剖析Android音频之AudioTrack

http://www.2cto.com/kf/201410/342659.html

Android Audio System 之一:AudioTrack如何与AudioFlinger交换音频数据

http://blog.csdn.net/droidphone/article/details/5941344

 

 

 

2.2  AudioFlinger(AF)

负责向下访问AudioHardwareInterface,实现音频PCM数据的混音/输入/输出以及音量调节;是底层和安卓层的桥梁。

文件位置: frameworks\av\services\audioflinger\ AudioFlinger.cpp

 

See also:

Android Audio System 之二:AudioFlinger

http://blog.csdn.net/onetwothreef/article/details/46311803

Android Audio System 之一:AudioTrack如何与AudioFlinger交换音频数据

http://blog.csdn.net/onetwothreef/article/details/46311645

Android深入浅出之Audio 第二部分 AudioFlinger分析

http://blog.csdn.net/onetwothreef/article/details/46311851

 

受用的评论:参见http://blog.csdn.net/droidphone/article/details/5951999

按照评论的理解,当手机里打开两个播放器的同时播放音乐,它们(不同的音乐)是同一个MixThread中的两个不同的AudioTrack(音轨),并混音输出。

 

 

2.3  AudioPolicyService(APS)

 AudioPolicyService主要完成以下任务:

  • JAVA应用层通过JNI,经由IAudioPolicyService接口,访问AudioPolicyService提供的服务
  • 输入输出设备的连接状态
  • 系统的音频策略(strategy)的切换
  • 音量/音频参数的设置

AudioPolicyManager

 

   AudioPolicyService的很大一部分管理工作都是在AudioPolicyManager中完成的。包括音量管理,音频策略(strategy)管理,输入输出设备管理。

 

 

See also:

Android Audio System 之三: AudioPolicyService 和 AudioPolicyManager

http://blog.csdn.net/onetwothreef/article/details/46311725

Android音频系统之AudioPolicyService

http://blog.csdn.net/onetwothreef/article/details/46311457

Android源码分析:AudioPolicy

http://www.360doc.com/content/13/0815/14/11338643_307326622.shtml

 

 

 

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。