iOS CoreAudio AudioStreamBasicDescription 音频格式概念简介

AudioStreamBasicDescription 简称 ASBDASBD 是 CoreAudio 用来指定线性 PCM 格式,或者使用 CBR 编码的等大小声道的格式。如果使用的是 VBR,或者使用非等大小的 CBR,需要对每个 packet 独立设置 AudioStreamPacketDescription进行描述。

在分析 ASBD 每个字段之前,我们先来搞懂几个概念:

  • Audio Stream: 一个 audio stream 表示一个声音的连续数据,比如一首歌
  • Channel:声道,一个声道是一个独立的音轨,单声道音频流只有一个 channel,立体声音频流有两个 channel
  • Sample:采样,一个采样对应一个 channel 里的一个具体的数字
  • Frame:一个 frame 包含一组相同时间的samples集合,比如一个线性立体声 PCM 文件每个 frame 包含两个 samples(左声道 sample 和 右声道 sample)
  • Packet: 一个 packet 包含一个或者多个连续的frame,在给定的音频数据格式的情况下,一个 packet 定义了一个最小有意义的 frame 集合,也是最小可测量时间的数据单位。 对于线性PCM音频这类非压缩格式,一个packet只包含一个frame
    对于压缩格式,一个 packet 通常会包含多个 frame,比如 AAC 可能会包含 1024 个 frame。
    对于某些格式,比如 Ogg,一个 packet 对应的 frame 数量可能是变化的,该字段填充 0。

一条 AudioStream 和 Channel、Sample、Frame、Packet 之间的关系如下图:

Image.png

然后来看一下 AudioStreamBasicDescription 的各个属性:

1
2
3
4
5
6
7
8
9
10
11
12
struct AudioStreamBasicDescription
{
Float64 mSampleRate;
AudioFormatID mFormatID;
AudioFormatFlags mFormatFlags;
UInt32 mBytesPerPacket;
UInt32 mFramesPerPacket;
UInt32 mBytesPerFrame;
UInt32 mChannelsPerFrame;
UInt32 mBitsPerChannel;
UInt32 mReserved;
};
  • mSampleRate, The number of sample frames per second of the data in the stream,注意这里说的是每秒钟的 frame 的个数,注意不是 sample 的个数
  • mFormatID,stream 里的数据类型
  • mFormatFlags,mFormatID 对应的格式 flags
  • mBytesPerPacket,每个 packet 的大小,单位是 byte
  • mFramesPerPacket,每个 packet 包含多少 frames(参考上文,线性 PCM 下,这里是 1)
  • mBytesPerFrame, 每个 frame 占多少 bytes
  • mChannelsPerFrame,每个 frame 包含几个 channel 的数据
  • mBitsPerChannel,一个 frame 里的一个 channel 数据站多少 bits,其实就是每个 sample 的大小,除以 8 就是占的字节数
  • mReserved,填充字段

根据上面的,我们可以得到这样的关系:

1
2
mBytesPerPacket = mFramesPerPacket * mBytesPerFrame
mBytesPerFrame = mChannelsPerFrame * mBitsPerChannel / 8

那么我们应该这么计算 一个 packet 的duration

1
duration = (1 / mSampleRate) * mFramesPerPacket

Ref:

AudioStreamBasicDescription