faac库编码PCM数据

1 篇文章 0 订阅
0 篇文章 0 订阅

简介

AAC(Advanced Audio Coding),一种音频编码技术。具体有哪些特点和优点,自行去百度或google吧。

函数简介

faac是一个成熟的AAC编码库。其提供的主要接口函数如下:

faacEncOpen
faacEncHandle FAACAPI faacEncOpen 
    (
        unsigned long sampleRate,
        unsigned int numChannels,
        unsigned long *inputSamples,
        unsigned long *maxOutputBytes      
     );

* sampleRate *:采样率
* numChannels *:声道数
* inputSamples * :编码时每次需要输入的字节数
* maxOutputBytes * : 编码时输出的最大字节数

该函数主要是创建一个编码器,并且返回需要输入的字节及编码返回的最大字节数

faacEncClose
void FAACAPI faacEncClose( faccEncHandle hEncoder);

与上述接口相对应,关闭编码器。

faacEncGetCurrentConfiguration
faacEncConfigurationPtr FAACAPI faacEncGetCurrentConfiguration( faccEncHandle hEncoder);

该函数获取当前编码器的配置

faacEncGetCurrentConfiguration
faacEncConfigurationPtr FAACAPI faacEncSetCurrentConfiguration
( 
    faccEncHandle hEncoder,
    faacEncConfigurationPtr config
);

该函数设置当前编码器的配置

faacEncEncode
int FAACAPI faacEncEncode
(
    faacEncHandle hEncoder,
   int32_t *inputBuffer,
    unsigned int samplesInput,
    unsigned char *outputBuffer,
    unsigned int bufferSize
);

* hEncoder *:编码器,通过faacEncOpen函数创建的
* inputBuffer *:输入数据
* sampleInput *:输入数据大小,如果为0,则编码器会把换成的数据都给输出
* outputBuffer *:存放输出数据
* bufferSize *:存放输出数据的缓存区大小,至少是和maxOutputBytes一样的大小

该函数进行编码

faacEncConfigurationPtr 结构
typedef struct faacEncConfiguration
{
    unsigned int mpegVersion;
    unsigned int aacObjectType;
    unsigned int allowMidside;
    unsigned int useLfe;
    unsigned int useTns;
    unsigned long bitRate;
    unsigned int bandWidth;
    ...
}
faacEncConfiguration, *faacEncConfigurationPtr;

简单的介绍其中的几个参数

mpegVersion :mpeg版本, MPEG2/MPEG4
aacObjectType:MAIN/LOW/LTP
allowMidside:mid/side coding
useLfe:低频增强
useTns:瞬时噪声定形(temporal noise shaping,TNS)滤波器
bitRate :码率
bandWidth:占用的带宽
outputFormat:输出格式,0 = Raw, 1 = ADTS
inputFormat:输入格式,FAAC_INPUT_NULL/FAAC_INPUT_16BIT/FAAC_INPUT_24BIT/FAAC_INPUT_32BIT/FAAC_INPUT_FLOAT
代码如下
/* aac_encode.c */
#include <stdio.h>
#include <faac.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>

int main (int argc, char **argv)
{
    unsigned long sampleRate = 8000;
    unsigned int numChannels = 1;
    unsigned long inputSample = 0;
    unsigned long maxOutputBytes = 0;
    faacEncHandle encoder;
    faacEncConfigurationPtr config;
    FILE *rfile = NULL;
    FILE *wfile = NULL;
    int16_t *pcm_input = NULL;
    uint8_t *aac_output = NULL;
    int readcount = 0;
    int writecount = 0;

    encoder = faacEncOpen(sampleRate, numChannels, &inputSample, &maxOutputBytes);
    config = faacEncGetCurrentConfiguration(encoder);
    config->aacObjectType = MAIN;
    config->mpegVersion = MPEG4;
    //config->useLfe = 1;
    config->useTns = 1;
    config->allowMidside = 1;
    config->outputFormat = 1;  // RAW_STREAM = 0, ADTS_STREAM 1
    //config->bitRate = ;
    config->inputFormat = FAAC_INPUT_16BIT;
    faacEncSetConfiguration(encoder, config);

    printf("sampleRate:%ld, numChannels:%d, inputSample:%ld, maxOutputBytes:%ld\n", 
            sampleRate, numChannels, inputSample, maxOutputBytes);

    if (argv[1]) {
        rfile = fopen(argv[1], "rb");
    } else {
        printf("try to open /tmp/input.pcm\n");
        rfile = fopen("/tmp/input.pcm", "rb");
    }

    if (!rfile) {
        printf("open error\n");
        goto end;
    }

    if (argv[2]) {
        wfile = fopen(argv[2], "wb");
    } else {
        printf("try to open /tmp/output.aac\n");
        wfile = fopen("/tmp/output.aac", "wb");
    }

    if (!wfile) {
        printf("open error\n");
        goto end;
    }

    pcm_input = (int16_t *)malloc(inputSample * sizeof(int16_t));
    aac_output = (uint8_t *)malloc(maxOutputBytes * sizeof(uint8_t));

    /* encode */
    while (1) {
        int readlen = 0;
        int ret = 0;

        readlen = fread(pcm_input, sizeof(int16_t), inputSample, rfile);

        //printf("====================read %d\n", readlen);
        ret = faacEncEncode(encoder, (int32_t *)pcm_input, readlen, aac_output, maxOutputBytes);

        if (ret > 0) {
            //printf("encode success! ret %d\n", ret);
            fwrite(aac_output, sizeof(uint8_t), ret, wfile);
        } else if (ret < 0) {
            printf("encode error\n");
            break;
        }

        readcount += readlen * 2;
        writecount += ret;

        if (!readlen && !ret) {
            printf("encode complete, from %d bytes to %d bytes\n", readcount, writecount);
            break;
        }
    }

    free(pcm_input);
    free(aac_output);

  end:
    if (wfile) fclose(wfile);
    if (rfile) fclose(rfile);
    faacEncClose(encoder);
    return 0;
}
/* Makefile */
all: aac

aac: aac_encode.c Makefile
    gcc -O3 -Wall -Werror -Wno-unused aac_encode.c -lfaac -o aac_enc

clean:
    rm -rf aac_enc

最后编译,运行即可

make
./aac_enc /tmp/北京北京8k16bits单声道.pcm /tmp/output.aac

使用播放器打开output.aac即可

注意:以上代码在MacOS 10.10.4 上编译并运行通过

  • 7
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值