AAC有两种格式,ADIF和ADTS,以下示例仅限ADTS。
#include <stdio.h>
#include <stdlib.h>
#include "faad.h"
// 读取aac文件内容到buffer
static unsigned char* getAacData(char *name, int *dataSize){
FILE *fp = fopen(name, "rb");
if(fp == NULL) return NULL;
fseek(fp, 0, SEEK_END);
int size = ftell(fp);
fseek(fp, 0, SEEK_SET);
unsigned char *buffer = malloc(size+16);
fread(buffer, size, 1, fp);
*dataSize = size;
fclose(fp);
return buffer;
}
int main(int argc, char* argv[]){
if(argc < 2) return 0;
int aacDataSize = 0;
unsigned char *aacData = getAacData(argv[1], &aacDataSize);
printf("aacDataSize = %d\n", aacDataSize);
// 打开faad2解码器
NeAACDecHandle faadHandle = NeAACDecOpen();
if(faadHandle == NULL) return -1;
// 解码之前需要初始化
unsigned char channels = 0;
unsigned long samplerate = 0;
long ret = NeAACDecInit(faadHandle, aacData, aacDataSize, &samplerate, &channels);
printf("ret = %ld, channels = %u, samplerate = %lu\n", ret, channels, samplerate);
// 循环解码
int aacOffset = 0;
void *sampleData = NULL;
NeAACDecFrameInfo frameInfo;
while(aacOffset < aacDataSize){
// faad2 解码
sampleData = NeAACDecDecode(faadHandle, &frameInfo, aacData+aacOffset, aacDataSize-aacOffset);
if((sampleData == NULL) || (frameInfo.error)) break;
// sampleData是解码出来的sample,注意不要free(sampleData)。
// frameInfo.bytesconsumed 是本次被解码掉的字节数
// frameInfo.samples 是sample个数
// frameInfo.samplerate 是频率
// frameInfo.channels 是通道数
printf("bytesconsumed = %lu, samples = %lu, samplerate = %lu, channels = %u\n",
frameInfo.bytesconsumed,
frameInfo.samples,
frameInfo.samplerate,
frameInfo.channels
);
aacOffset += frameInfo.bytesconsumed;
}
// 关闭解码器
NeAACDecClose(faadHandle);
free(aacData);
return 0;
}
遇到过5.1声道的情况,经过探索,解码出来的5.1声道PCM内存布局应该是这样的:
[正中声道, 左声道, 右声道, 左环绕, 右环绕, 低频增强]
。
5.1声道转2声道采取以下算法效果较好:
左 = 正中声道 + 左声道 + 左环绕 + 低频增强;
右 = 正中声道 + 右声道 + 右环绕 + 低频增强;
网友评论