当前位置:网站首页>Audio codec, using FAAC to implement AAC encoding
Audio codec, using FAAC to implement AAC encoding
2022-08-11 03:26:00 【Audio and video development old man】
这里利用FAAC来实现AAC编码.另外,WAV的数据段是PCM,代码会出现很多PCM缩写.
1 下载安装 FAAC
这里的安装过程是在 Mac 和 Linux 上实现的,Windows可以类似参考.
wget http://downloads.sourceforge.net/faac/faac-1.28.tar.gz
tar zxvf faac-1.28.tar.gz
cd faac-1.28
./configure
make
sudo make install
如果才用默认的 configure 中的 prefix path,那么安装后的 lib 和 .h 文件分别在/usr/local/lib和/usr/local/include,后面编译的时候会用到.
2 FAAC API
2.1 Open FAAC engine
Prototype:
faacEncHandle faacEncOpen // 返回一个FAAC的handle
(
unsigned long nSampleRate, // 采样率,单位是bps
unsigned long nChannels, // 声道,1为单声道,2为双声道
unsigned long &nInputSamples, // 传引用,得到每次调用编码时所应接收的原始数据长度
unsigned long &nMaxOutputBytes // 传引用,得到每次调用编码时生成的AAC数据的最大长度
);
本文福利, C++音视频学习资料包、技术视频,内容包括(音视频开发,面试题,FFmpeg ,webRTC ,rtmp ,hls ,rtsp ,ffplay ,srs)↓↓↓↓↓↓见下面↓↓文章底部点击领取↓↓
2.2 Get/Set encoding configuration
Prototype:
获取编码器的配置:
faacEncConfigurationPtr faacEncGetCurrentConfiguration // 得到指向当前编码器配置的指针
(
faacEncHandle hEncoder // FAAC的handle
);
设定编码器的配置:
int FAACAPI faacEncSetConfiguration
(
faacDecHandle hDecoder, // 此前得到的FAAC的handle
faacEncConfigurationPtr config // FAAC编码器的配置
);
2.3 Encode
Prototype:
int faacEncEncode
(
faacEncHandle hEncoder, // FAAC的handle
short *inputBuffer, // WAV原始数据
unsigned int samplesInput, // 调用faacEncOpen时得到的nInputSamples值
unsigned char *outputBuffer,// 至少具有调用faacEncOpen时得到的nMaxOutputBytes字节长度的缓冲区
unsigned int bufferSize // outputBuffer缓冲区的实际大小
);
2.4 Close FAAC engine
Prototype
void faacEncClose
(
faacEncHandle hEncoder // 此前得到的FAAC handle
);
3 流程
3.1 做什么准备?
采样率,声道数(双声道还是单声道?),还有你的WAV的单个样本是8位的还是16位的?
3.2 开启FAAC编码器,做编码前的准备
- 调用
faacEncOpen开启FAAC编码器后,得到了单次输入样本数nInputSamples和输出数据最大字节数nMaxOutputBytes; - 根据
nInputSamples和nMaxOutputBytes,分别为WAV数据和将要得到的AAC数据创建缓冲区; - 调用
faacEncGetCurrentConfiguration获取当前配置,修改完配置后,调用faacEncSetConfiguration设置新配置.
3.3 开始编码
调用faacEncEncode,该准备的刚才都准备好了,很简单.
3.4 善后
关闭编码器,另外别忘了释放缓冲区,如果使用了文件流,也别忘记了关闭.
4 测试程序
4.1 完整代码
将WAV格式音频文件/home/michael/Development/testspace/in.wav转至AAC格式文件/home/michael/Development/testspace/out.aac.
#include <faac.h>
#include <stdio.h>
typedef unsigned long ULONG;
typedef unsigned int UINT;
typedef unsigned char BYTE;
typedef char _TCHAR;
int main(int argc, _TCHAR* argv[])
{
ULONG nSampleRate = 11025; // 采样率
UINT nChannels = 1; // 声道数
UINT nPCMBitSize = 16; // 单样本位数
ULONG nInputSamples = 0;
ULONG nMaxOutputBytes = 0;
int nRet;
faacEncHandle hEncoder;
faacEncConfigurationPtr pConfiguration;
int nBytesRead;
int nPCMBufferSize;
BYTE* pbPCMBuffer;
BYTE* pbAACBuffer;
FILE* fpIn; // WAV file for input
FILE* fpOut; // AAC file for output
fpIn = fopen("/home/michael/Development/testspace/in.wav", "rb");
fpOut = fopen("/home/michael/Development/testspace/out.aac", "wb");
// (1) Open FAAC engine
hEncoder = faacEncOpen(nSampleRate, nChannels, &nInputSamples, &nMaxOutputBytes);
if(hEncoder == NULL)
{
printf("[ERROR] Failed to call faacEncOpen()\n");
return -1;
}
nPCMBufferSize = nInputSamples * nPCMBitSize / 8;
pbPCMBuffer = new BYTE [nPCMBufferSize];
pbAACBuffer = new BYTE [nMaxOutputBytes];
// (2.1) Get current encoding configuration
pConfiguration = faacEncGetCurrentConfiguration(hEncoder);
pConfiguration->inputFormat = FAAC_INPUT_16BIT;
// (2.2) Set encoding configuration
nRet = faacEncSetConfiguration(hEncoder, pConfiguration);
for(int i = 0; 1; i++)
{
// 读入的实际字节数,最大不会超过nPCMBufferSize,一般只有读到文件尾时才不是这个值
nBytesRead = fread(pbPCMBuffer, 1, nPCMBufferSize, fpIn);
// 输入样本数,用实际读入字节数计算,一般只有读到文件尾时才不是nPCMBufferSize/(nPCMBitSize/8);
nInputSamples = nBytesRead / (nPCMBitSize / 8);
// (3) Encode
nRet = faacEncEncode(
hEncoder, (int*) pbPCMBuffer, nInputSamples, pbAACBuffer, nMaxOutputBytes);
fwrite(pbAACBuffer, 1, nRet, fpOut);
printf("%d: faacEncEncode returns %d\n", i, nRet);
if(nBytesRead <= 0)
{
break;
}
}
// (4) Close FAAC engine
nRet = faacEncClose(hEncoder);
delete[] pbPCMBuffer;
delete[] pbAACBuffer;
fclose(fpIn);
fclose(fpOut);
//getchar();
return 0;
}
4.2 编译运行
将上述代码保存为“wav2aac.cpp”文件,然后编译:
g++ wav2aac.cpp -o wav2aac -L/usr/local/lib -lfaac -I/usr/local/include
运行:
./wav2aac
然后就生成了out.aac文件了,听听看吧!~
本文福利, C++音视频学习资料包、技术视频,内容包括(音视频开发,面试题,FFmpeg ,webRTC ,rtmp ,hls ,rtsp ,ffplay ,srs)↓↓↓↓↓↓见下面↓↓文章底部点击领取↓↓
边栏推荐
- 荣威imax8ev魔方电池安全感,背后隐藏着哪些黑化膨胀?
- DOM-DOM tree, a DOM tree has three types of nodes
- typedef定义结构体数组类型
- 高度塌陷问题的解决办法
- Window function application of sum and count
- The 125th day of starting a business - a note
- Getting Started with Raspberry Pi (5) System Backup
- 大马驮2石粮食,中马驮1石粮食,两头小马驮一石粮食,要用100匹马,驮100石粮食,如何分配?
- 浅析一下期货程序化交易好还是手工单好?
- 【LeetCode】Day112-重复的DNA序列
猜你喜欢

Is Redis old?Performance comparison between Redis and Dragonfly

CTO说MySQL单表行数不要超过2000w,为啥?

高校就业管理系统设计与实现

【愚公系列】2022年08月 Go教学课程 036-类型断言

Google search skills - programmer is recommended

How does MSP430 download programs to the board?(IAR MSPFET CCS)

rac备库双节点查询到的表最后更新时间不一致

E-commerce project - mall time-limited seckill function system

"How to kick a bad habit to read notes?
![[DB operation management/development solution] Shanghai Daoning provides you with an integrated development tool to improve the convenience of work - Orange](/img/3e/06654c5ad976bad53bf0aa4390e7e9.png)
[DB operation management/development solution] Shanghai Daoning provides you with an integrated development tool to improve the convenience of work - Orange
随机推荐
浮点数在内存中的存储方式
The negative semantic transformation layer
rac备库双节点查询到的表最后更新时间不一致
音频编解码,利用FAAC来实现AAC编码
80端口和443端口是什么?有什么区别?
调试技巧总结
Salesforce解散中国团队,什么样的CRM产品更适合中国人
获取链表长度
A large horse carries 2 stone of grain, a middle horse carries 1 stone of grain, and two ponies carry one stone of grain. It takes 100 horses to carry 100 stone of grain. How to distribute it?
Qnet Weak Network Test Tool Operation Guide
学编程的第十三天
21 Day Learning Challenge Week 1 Summary
EasyCVR接入GB28181设备时,设备接入正常但视频无法播放是什么原因?
js中的this问题
Goodbye Chongqing paper invoices!The issuance of electronic invoices for accommodation expenses will soon completely replace the invoices of hotels, catering and gas stations
重庆纸质发票再见!开住宿费电子发票即将全面取代酒店餐饮加油站发票
Homework 8.10 TFTP protocol download function
[yu gong series] Go program 035-08 2022 interfaces and inheritance and transformation and empty interface
荣威imax8ev魔方电池安全感,背后隐藏着哪些黑化膨胀?
uni-app - 获取汉字拼音首字母(根据中文获取拼音首字母)