AAC编码可以使用faac

/**
初始化 @param sampleRate 音频采样率
@param channels 通道数
@param bitSize 音频采样精度 16
*/
- (void)initWithSampleRate:(int)sampleRate channels:(int)channels bitSize:(int)bitSize
{
nSampleRate = sampleRate;
nChannels = channels;
nPCMBitSize = bitSize; hEncoder = faacEncOpen(nSampleRate,nChannels,&nInputSamples,&nMaxOutputBytes);
if(hEncoder == NULL)
{
error = -;
}
int pcmBufSize = (int)(nInputSamples*(nPCMBitSize/)); // 固定计算方式
pcmBuf = (unsigned char *)malloc(pcmBufSize * sizeof(unsigned char)); // pcmBufSize* 1个字节
memset(pcmBuf,,pcmBufSize);
aacBuf = (unsigned char *)malloc(nMaxOutputBytes * sizeof(unsigned char));
memset(aacBuf,,nMaxOutputBytes); faacEncConfigurationPtr config = faacEncGetCurrentConfiguration(hEncoder);
config->aacObjectType = LOW; //LC编码 编码类型
config->inputFormat = FAAC_INPUT_16BIT; //输入数据类型
config->outputFormat = ; //录制MP4文件时,0要用raw流; 1是ADTS
int ret = faacEncSetConfiguration(hEncoder, config);
if (ret < ) {
error = -;
}
}
/**
编码 @param data pcm
@param dataSize 长度
*/
-(void)encoderWithData:(unsigned char *)data dataSize:(int)dataSize
{
if (error<) {
return;
} // 2048 4096
int pcmBufSize = (int)(nInputSamples*(nPCMBitSize/)); // 固定计算方式 if(data == NULL||dataSize<=|| dataSize > pcmBufSize){
NSLog(@"error:dataSize大于填充大小");
return;
} int copyLength = ; if(remainBufSize > dataSize){
copyLength = dataSize;
}
else{
copyLength = remainBufSize;
}
memcpy((&pcmBuf[]) + remainWriteSize,data,copyLength); remainBufSize -= copyLength;
remainWriteSize += copyLength; if(remainBufSize > ){
return;
}
int ret = faacEncEncode(hEncoder,(int*)(pcmBuf),(unsigned int)nInputSamples,aacBuf,(unsigned int)nMaxOutputBytes);
if (ret<) {
return;
}
if ([self.delegate respondsToSelector:@selector(AACEncoderData:dataSize:)]) {
if (ret>) {
[self.delegate AACEncoderData:aacBuf dataSize:ret];
} } memset(pcmBuf, , pcmBufSize);
remainWriteSize = ;
remainBufSize = pcmBufSize;
if((dataSize - copyLength) > ){
memcpy((&pcmBuf[]), data+copyLength, dataSize - copyLength);
remainWriteSize = dataSize - copyLength; // 已经填了多少
remainBufSize = pcmBufSize - (dataSize - copyLength); // 还差多少填满 2048
}
}

AAC解码可以使用faad

@implementation AACDecoder
- (instancetype)init
{
self = [super init];
if (self) {
decoder = NeAACDecOpen();
samplerate = ;
channels = ;
pcmData = NULL;
size = ;
}
return self;
}
/**
解码 @param data aac
@param dataSize 长度
*/
-(void)decoderWithData:(unsigned char *)data dataSize:(int)dataSize
{
if (!loaded) { if(getOneADTSFrame(data, dataSize, frame, &size)== )
{
NeAACDecInit(decoder, frame, size, &samplerate, &channels);
printf("samplerate %lu, channels %d\n", samplerate, channels);
loaded = YES;
}
}
while(getOneADTSFrame(data,dataSize,frame,&size) == )
{
pcmData = (unsigned char*)NeAACDecDecode(decoder, &frameInfo,frame,size);
if(frameInfo.error > )
{
printf("%s\n",NeAACDecGetErrorMessage(frameInfo.error)); }
else if(pcmData && frameInfo.samples > )
{
printf("frame info: bytesconsumed %lu, channels %d, header_type %d\
object_type %d, samples %lu, samplerate %lu\n",
frameInfo.bytesconsumed,
frameInfo.channels, frameInfo.header_type,
frameInfo.object_type, frameInfo.samples,
frameInfo.samplerate); if ([self.delegate respondsToSelector:@selector(AACDcoderData:dataSize:)]) {
[self.delegate AACDcoderData:pcmData dataSize:(int)(frameInfo.samples * frameInfo.channels)];
}
}
dataSize -= size;
data += size;
}
if ([self.delegate respondsToSelector:@selector(AACDcoderEnd)]) {
[self.delegate AACDcoderEnd];
} } - (void)dealloc
{
NeAACDecClose(decoder);
}
/**
* fetch one ADTS frame 获取一个ADTS Frame
*/
int getOneADTSFrame(unsigned char* buffer, size_t buf_size, unsigned char* data ,size_t* data_size)
{
size_t size = ; if(!buffer || !data || !data_size )
{
return -;
} while()
{
if(buf_size < )
{
return -;
} if((buffer[] == 0xff) && ((buffer[] & 0xf0) == 0xf0) )
{
size |= ((buffer[] & 0x03) <<); //high 2 bit
size |= buffer[]<<; //middle 8 bit
size |= ((buffer[] & 0xe0)>>); //low 3bit
break;
}
--buf_size;
++buffer;
} if(buf_size < size)
{
return -;
} memcpy(data, buffer, size);
*data_size = size; return ;
}

AAC编解码的更多相关文章

  1. 转载:AAC编解码概述

    转自:http://www.cnblogs.com/gaozehua/archive/2012/05/03/2479960.html 编码概述 其整体AAC 编解码系统,如图所示,其编码流程概述如下: ...

  2. 各种音视频编解码学习详解 h264 ,mpeg4 ,aac 等所有音视频格式

    编解码学习笔记(一):基本概念 媒体业务是网络的主要业务之间.尤其移动互联网业务的兴起,在运营商和应用开发商中,媒体业务份量极重,其中媒体的编解码服务涉及需求分析.应用开发.释放 license收费等 ...

  3. 视音频编解码学习工程:AAC格式分析器

    =====================================================视音频编解码学习工程系列文章列表: 视音频编解码学习工程:H.264分析器 视音频编解码学习工 ...

  4. 【FFMPEG】各种音视频编解码学习详解 h264 ,mpeg4 ,aac 等所有音视频格式

    目录(?)[-] 编解码学习笔记二codec类型 编解码学习笔记三Mpeg系列Mpeg 1和Mpeg 2 编解码学习笔记四Mpeg系列Mpeg 4 编解码学习笔记五Mpeg系列AAC音频 编解码学习笔 ...

  5. ffmpeg编解码音频AAC

    本次项目的需求:手机端和PC端共享同一个音视频网络源. 所以编解码需要满足手机上编码和解码原来PC端的音视频流. 这里先封装安卓手机端音频的编解码. 编译工作依然是在linux下 ubuntu 12. ...

  6. [总结]FFMPEG视音频编解码零基础学习方法--转

    ffmpeg编解码学习   目录(?)[-] ffmpeg程序的使用ffmpegexeffplayexeffprobeexe 1 ffmpegexe 2 ffplayexe 3 ffprobeexe ...

  7. FFMPEG视音频编解码零基础学习方法

    在CSDN上的这一段日子,接触到了很多同行业的人,尤其是使用FFMPEG进行视音频编解码的人,有的已经是有多年经验的“大神”,有的是刚开始学习的初学者.在和大家探讨的过程中,我忽然发现了一个问题:在“ ...

  8. FFMPEG视音频编解码零基础学习方法-b

    感谢大神分享,虽然现在还看不懂,留着大家一起看啦 PS:有不少人不清楚“FFmpeg”应该怎么读.它读作“ef ef em peg” 0. 背景知识 本章主要介绍一下FFMPEG都用在了哪里(在这里仅 ...

  9. android MediaCodec 音频编解码的实现——转码

    原文地址:http://blog.csdn.net/tinsanmr/article/details/51049179 从今天开始 每周不定期更新博客,把这一周在工作与学习中遇到的问题做个总结.俗话说 ...

随机推荐

  1. canvas中遇到的理解问题

    1.lineDashOffset ctx.lineDashOffset = number 描述: setLineDash 用于设置开始绘制虚线的偏移量. 数字的正负表示左右偏移. 2.createLi ...

  2. 利用Python网络爬虫抓取微信好友的所在省位和城市分布及其可视化

    前几天给大家分享了如何利用Python网络爬虫抓取微信好友数量以及微信好友的男女比例,感兴趣的小伙伴可以点击链接进行查看.今天小编给大家介绍如何利用Python网络爬虫抓取微信好友的省位和城市,并且将 ...

  3. LG Gram 2018 z980 白

    因为今年8代处理器i5的双核变成了四核,感觉是个换电脑的好时机,本来打算买macbook,但是6月的发布会并没有发布,于是开始寻找一些比较有特点的笔记本电脑. 了解了这样一款笔记本 LG GRAM 1 ...

  4. 学习参考《Python数据分析与挖掘实战(张良均等)》中文PDF+源代码

    学习Python的主要语法后,想利用python进行数据分析,感觉<Python数据分析与挖掘实战>可以用来学习参考,理论联系实际,能够操作数据进行验证,基础理论的内容对于新手而言还是挺有 ...

  5. ZOJ 2532 Internship

    Internship Time Limit: 5000ms Memory Limit: 32768KB This problem will be judged on ZJU. Original ID: ...

  6. VIjos——V 1782 借教室 | | 洛谷——P1083 借教室

    https://vijos.org/p/1782|| https://www.luogu.org/problem/show?pid=1083 描述 在大学期间,经常需要租借教室.大到院系举办活动,小到 ...

  7. HDU 2886 Lou 1 Zhuang

    思维好重要.. 对于n+m == k , 当n == m || abs(n-m) == 1 时n*m取得最大值. 设 s = x*(l-x),s = lx-x^2.其导函数为 s' = -1/2x + ...

  8. 6.前端开发必备!Emmet使用手册

    转自:https://www.w3cplus.com/tools/emmet-cheat-sheet.html 介绍 Emmet (前身为 Zen Coding) 是一个能大幅度提高前端开发效率的一个 ...

  9. Intellij IDEA 部署Web项目,解决 404 错误

    https://blog.csdn.net/eaphyy/article/details/72513914

  10. vue 点击事件阻止冒泡 用stop

    1.使用vue阻止子级元素的click事件冒泡,很简单,用stop.eg: @click.stop='xxx'