`
Poechant
  • 浏览: 227601 次
博客专栏
Bebe66e7-3a30-3fc9-aeea-cfa3b474b591
Nginx高性能Web服务...
浏览量:24243
5738817b-23a1-3a32-86de-632d7da73b1e
Cumulus实时媒体服务...
浏览量:22051
社区版块
存档分类
最新评论

音频编解码·实战篇(1)PCM转至AAC(AAC编码)

 
阅读更多

音频编解码·实战篇(1)PCM转至AAC(AAC编码)

  • 作者:柳大·Poechant
  • 博客:blog.csdn.net/poechant
  • 邮箱:zhongchao.ustc@gmail.com
  • 日期:April 7th, 2012

这里利用FAAC来实现AAC编码。

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,后面编译的时候会用到。

如果编译过程中发现错误:

mpeg4ip.h:126: error: new declaration ‘char* strcasestr(const char*, const char*)’

解决方法:

从123行开始修改此文件mpeg4ip.h,到129行结束。 修改前:

#ifdef __cplusplus
extern "C" {
#endif
char *strcasestr(const char *haystack, const char *needle);
#ifdef __cplusplus
}
#endif

修改后:

#ifdef __cplusplus
extern "C++" {
#endif
const char *strcasestr(const char *haystack, const char *needle);
#ifdef __cplusplus
}
#endif

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数据的最大长度
);

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,         // PCM原始数据
    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 做什么准备?

采样率,声道数(双声道还是单声道?),还有你的PCM的单个样本是8位的还是16位的?

3.2 开启FAAC编码器,做编码前的准备

  1. 调用faacEncOpen开启FAAC编码器后,得到了单次输入样本数nInputSamples和输出数据最大字节数nMaxOutputBytes
  2. 根据nInputSamplesnMaxOutputBytes,分别为PCM数据和将要得到的AAC数据创建缓冲区;
  3. 调用faacEncGetCurrentConfiguration获取当前配置,修改完配置后,调用faacEncSetConfiguration设置新配置。

3.3 开始编码

调用faacEncEncode,该准备的刚才都准备好了,很简单。

3.4 善后

关闭编码器,另外别忘了释放缓冲区,如果使用了文件流,也别忘记了关闭。

4 测试程序

4.1 完整代码

PCM格式音频文件/home/michael/Development/testspace/in.pcm转至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; // PCM file for input
    FILE* fpOut; // AAC file for output

    fpIn = fopen("/home/michael/Development/testspace/in.pcm", "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;
        }
    }

    /*
    while(1)
    {
        // (3) Flushing
        nRet = faacEncEncode(
        hEncoder, (int*) pbPCMBuffer, 0, pbAACBuffer, nMaxOutputBytes);

        if(nRet <= 0)
        {
            break;
        }
    }
    */

    // (4) Close FAAC engine
    nRet = faacEncClose(hEncoder);

    delete[] pbPCMBuffer;
    delete[] pbAACBuffer;
    fclose(fpIn);
    fclose(fpOut);

    //getchar();

    return 0;
}

4.2 编译运行

将上述代码保存为“pcm2aac.cpp”文件,然后编译:

g++ pcm2aac.cpp -o pcm2aac -L/usr/local/lib -lfaac -I/usr/local/include

运行:

./pcm2aac

然后就生成了out.aac文件了,听听看吧!~

5 Reference

  1. AudioCoding.com - FAAC
  2. Dogfoot – 재밌는 개발

-

转载请注明来自柳大的CSDN博客:blog.csdn.net/poechant

-

分享到:
评论

相关推荐

    speex音频转pcm和aac

    在音频处理领域,Speex、PCM和AAC是三种常见的音频编码格式,每种都有其特定的应用场景和优势。本文将详细讲解如何将Speex音频转换为PCM和AAC,以及链表类在其中的作用。 首先,让我们了解这三种音频格式: 1. ...

    音频类型转换,如G711转AAC、PCM转AAC等

    将G711音频转换为AAC,首先需要解码G.711信号,将其恢复为原始的PCM(脉冲编码调制)音频数据。PCM是数字音频的基本表示形式,它直接存储声音波形的样点。然后,这个PCM数据会通过AAC编码器进行编码,利用AAC的压缩...

    pcm音频转aac

    要进行PCM到AAC的转换,你需要一个编码库,如FFmpeg,它是一个强大的多媒体处理工具,支持多种音频和视频格式的编码、解码、转换和流媒体操作。在Linux平台上,你可以按照以下步骤来编译和使用FFmpeg进行音频转码: ...

    FAAD2解码AAC,生成PCM文件,转换WAV格式

    在IT领域,音频编码与解码是至关重要的技术,尤其在多媒体处理中。本文将深入讲解如何使用FAAD2解码AAC(Advanced Audio Coding)文件,并生成PCM(Pulse Code Modulation)文件,最终将其转换为WAV格式。首先,我们...

    aac转换为pcm

    转换过程的核心是音频编解码器,faac库就是这样一个工具,它提供了AAC编码的功能。faac是一个开源的AAC编码器,支持MPEG-4 AAC LC(Low Complexity)和HE-AAC(High Efficiency AAC)标准。使用faac,我们可以将音频...

    FFMPEG实现PCM编码AAC和MP3(采用封装格式实现)

    1. **PCM编码**:PCM是数字音频的基本编码方式,它直接将模拟信号转换为数字序列,保留原始音频的所有细节。在FFmpeg中,PCM数据可以是单声道或立体声,不同位深度(如16位或24位)表示不同的音频质量。 2. **AAC...

    Android录音,PCM音频编码AAC格式

    Android的`MediaCodec`类提供了硬件加速的多媒体编码和解码能力,包括将PCM数据编码为AAC。`MediaCodec`是一个低级别的API,可以处理各种编码标准,如H.264视频编码和AAC音频编码。使用`MediaCodec`进行音频编码时,...

    Windos音频编解码

    1. **音频编解码**:音频编解码是将模拟音频信号转化为数字信号的过程,包括编码(压缩)和解码(解压)。编码旨在减少数据量,便于存储和传输,而解码则将压缩后的数据还原为原始音频格式。常见的音频编码格式有MP3...

    G722音频编解码

    G722音频编解码是一种广泛应用于网络通信中的音频编码技术,特别是在VoIP(Voice over Internet Protocol)和视频会议系统中。它基于ITU-T G.722标准,旨在提供高质量、全双工的音频传输,适用于64kbps的带宽。以下...

    ffmpeg之pcm转AAC

    在本话题中,我们将深入探讨如何使用FFmpeg将PCM(脉冲编码调制)音频数据转换为AAC(高级音频编码)格式。 PCM是未经压缩的原始音频数据,通常占用大量存储空间,而AAC是一种高效的有损音频编码标准,能够在保持较...

    解码aac音频转pcm(使用faad2库)

    1. 使用faad2库解码aac音频转为pcm文件。 2. 支持vs2017 & linux环境下gcc编译(linuxx使用的gcc版本为4.8.5,系统为centos7.8)。 3. faad2库使用的2_9_1版本,源码放在depend目录下,打开depends\faad\faad2.sln可...

    音频G711转PCM;PCM转AAC;demo VS2010下编译运行

    在音频处理领域,编码与解码是至关重要的环节,尤其是对于不同格式的音频转换。本文将深入探讨"音频G711转PCM;PCM转AAC"这一主题,并提供在Visual Studio 2010环境下编译运行的DEMO示例。 首先,我们要了解G.711和...

    fdk aac aac编解码库

    1. **码率控制精准**:FDK-AAC库在编码过程中能够精确控制输出码率,这对于需要在特定带宽下保持音频质量的应用非常重要。这种能力使得它在广播、流媒体等领域有着广泛的应用。 2. **HE-AAC支持**:High Efficiency...

    pcm编码aac

    PCM编码和AAC编码是音频处理领域中的两种重要技术,它们分别代表了无损和有损音频编码的标准。在本文中,我们将深入探讨这两种编码方式,以及如何使用libfdk-aac库将PCM编码为AAC。 PCM(Pulse Code Modulation,...

    aac pcm 编解码

    在移动设备上进行音频处理时,AAC (Advanced Audio Coding)、PCM (Pulse Code Modulation) 和 AMR (Adaptive Multi-Rate) 是常见的音频编解码格式。这些格式各有特点,适用于不同的应用场景。本篇文章将详细介绍AAC...

    Android MediaCodec解码AAC,AudioTrack播放PCM音频

    在这个特定的示例中,我们关注的是如何使用MediaCodec解码AAC(Advanced Audio Coding)音频,并通过AudioTrack将其播放出来。让我们深入探讨这个过程的细节。 首先,AAC是一种高效的有损音频压缩格式,广泛应用于...

    linux下aac解码成pcm

    压缩包中的"ADTS-AAC解码pcm"可能是示例代码、解码示例AAC文件或readme文档,它会提供更详细的实现步骤和可能遇到的问题。阅读这些内容可以帮助你更好地理解libfaad的工作原理和实际应用。 总的来说,使用libfaad在...

    Android G711(PCMA/PCMU)、G726、PCM音频转码到AAC

    1. **音频解码**:首先,需要解码G711或G726编码的音频数据。这通常涉及解析编码后的字节流并将其转化为原始PCM样本。对于G711,可以使用标准的解码函数,如`alaw_to-linear`和`ulaw_to-linear`。G726的解码则需要...

    C++ 使用fdk-aac对音频编码

    mp4的音频流通常是aac编码,我们做音视频采集的时候就需要将,采集的音频PCM编码成aac,然后再打包进mp4,而aac编解码库中fdk-aac是性能较好的,使用方式也比较简单。在C++项目中使用,通常再做一层封装,提高模块的...

Global site tag (gtag.js) - Google Analytics