zoukankan      html  css  js  c++  java
  • FFMPEG more samples than frame size (avcodec_encode_audio2) 的解决方案

    在实际的项目中,从音频设备采集到的音频的类型和编码器类型(aac ,amr)通常是不一致的。

    那么我们首先需要做重采样的过程。利用swr_convert 重新采样。

    这时候我们可能会遇到另外一个问题。就是在encode_audio的时候遇到

    more samples than frame size (avcodec_encode_audio2)  的问题。

    问题的原因在于 我们编码器的frame_size 比采集到的fram->nb_samples小

    [cpp] view plaincopy在CODE上查看代码片派生到我的代码片
     
    1. /* check for valid frame size */  
    2.     if (frame) {  
    3.         if (avctx->codec->capabilities & CODEC_CAP_SMALL_LAST_FRAME) {  
    4.             if (frame->nb_samples > avctx->frame_size) {  
    5.                 av_log(avctx, AV_LOG_ERROR, "more samples than frame size (avcodec_encode_audio2) ");  
    6.                 return AVERROR(EINVAL);  
    7.             }  
    8.         } else if (!(avctx->codec->capabilities & CODEC_CAP_VARIABLE_FRAME_SIZE)) {  
    9.             if (frame->nb_samples < avctx->frame_size &&  
    10.                 !avctx->internal->last_audio_frame) {  
    11.                 ret = pad_last_frame(avctx, &padded_frame, frame);  
    12.                 if (ret < 0)  
    13.                     return ret;  
    14.   
    15.                 frame = padded_frame;  
    16.                 avctx->internal->last_audio_frame = 1;  
    17.             }  
    18.   
    19.             if (frame->nb_samples != avctx->frame_size) {  
    20.                 av_log(avctx, AV_LOG_ERROR, "nb_samples (%d) != frame_size (%d) (avcodec_encode_audio2) ", frame->nb_samples, avctx->frame_size);  
    21.                 ret = AVERROR(EINVAL);  
    22.                 goto end;  
    23.             }  
    24.         }  
    25.     }  


    解决的方案是:每次采集到的frame数据保存到一个AUDIO FIFO中,每次等凑齐刚好frame_size大小的数据(请注意这里是刚好,网上有人说拆分AVframe,本人在ffmpeg2.1用这个办法没办法解决),接着把这些数据一口气encode。

    如果有剩余的数据就存储到下一次encode。可以使用audio_fifo_来操作数据

    http://www.ffmpeg.org/doxygen/1.0/audio__fifo_8c-source.html

    http://blog.csdn.net/zsc09_leaf/article/details/16858193

    参考transcode_aac.c即可

  • 相关阅读:
    并发基础(一) 线程介绍
    java基础(九) 可变参数列表介绍
    全球 43 亿 IPv4 地址已耗尽!IPv6,刻不容缓
    IPv6,无需操作就可升级?
    为什么 HTTPS 比 HTTP 安全
    从《国产凌凌漆》看到《头号玩家》,你就能全面了解5G
    再谈 APISIX 高性能实践
    API 网关的选型和持续集成
    尹吉峰:使用 OpenResty 搭建高性能 Web 应用
    鱼和熊掌可兼得?一文看懂又拍云 SCDN
  • 原文地址:https://www.cnblogs.com/youngt/p/3771977.html
Copyright © 2011-2022 走看看