首页 > 代码库 > 最简单的基于FFmpeg的内存读写的例子:内存转码器

最简单的基于FFmpeg的内存读写的例子:内存转码器

上篇文章记录了一个基于FFmpeg的内存播放器,可以使用FFmpeg读取并播放内存中的数据。这篇文章记录一个基于FFmpeg的内存转码器。该转码器可以使用FFmpeg读取内存中的数据,转码为H.264之后再将数据输出到内存。
关于如何从内存读取数据,以及如何将数据输出到内存,可以参考文章:

 ffmpeg 从内存中读取数据(或将数据输出到内存)

FFmpeg读写内存的关键点有2个:
1.       初始化自定义的AVIOContext,指定自定义的回调函数。
2.       自己写回调函数。注意函数的参数和返回值(尤其是返回值)。
 
 
转码实际上就是解码和编码的结合。该方面的知识可以参考文章:

解码:100行代码实现最简单的基于FFMPEG+SDL的视频播放器(SDL1.x)

编码:最简单的基于FFMPEG的视频编码器(YUV编码为H.264)

转码: 最简单的基于FFMPEG的转码程序 

 

流程

程序的流程图如下图所示。从图中可以看出,首先分别初始化了输入和输出的AVFormatContext。然后首先解码输入的AVPacket,得到存储像素数据(YUV420P格式)的AVFrame,然后编码AVFrame为H.264的AVPacket,最后将编码后的AVPacket输出。
 

 代码

下面直接贴上代码:
 
 
/**
 * 最简单的基于FFmpeg的内存读写例子(内存转码器)
 * Simplest FFmpeg mem Transcoder
 *
 * 雷霄骅,张晖
 * leixiaohua1020@126.com
 * 中国传媒大学/数字电视技术
 * Communication University of China / Digital TV Technology
 * http://blog.csdn.net/leixiaohua1020
 *
 * 本程序实现了任意格式视频数据(例如MPEG2)转码为H.264码流数据。
 * 本程序并不是对文件进行处理,而是对内存中的视频数据进行处理。
 * 它从内存读取数据,并且将转码后的数据输出到内存中。
 * 是最简单的使用FFmpeg读写内存的例子。
 *
 * This software convert video bitstream (Such as MPEG2) to H.264
 * bitstream. It read video bitstream from memory (not from a file),
 * convert it to H.264 bitstream, and finally output to another memory.
 * It‘s the simplest example to use FFmpeg to read (or write) from 
 * memory.
 *
 */
#include <stdio.h>

extern "C"
{
#include "libavcodec/avcodec.h"
#include "libavformat/avformat.h"
#include "libavutil/avutil.h"
#include "libavutil/opt.h"
#include "libavutil/pixdesc.h"
};

FILE *fp_open;
FILE *fp_write;

//Read File
int read_buffer(void *opaque, uint8_t *buf, int buf_size){
	if(!feof(fp_open)){
		int true_size=fread(buf,1,buf_size,fp_open);
		return true_size;
	}else{
		return -1;
	}
}

//Write File
int write_buffer(void *opaque, uint8_t *buf, int buf_size){
	if(!feof(fp_write)){
		int true_size=fwrite(buf,1,buf_size,fp_write);
		return true_size;
	}else{
		return -1;
	}
}



int flush_encoder(AVFormatContext *fmt_ctx,unsigned int stream_index)
{
    int ret;
    int got_frame;
	AVPacket enc_pkt;
    if (!(fmt_ctx->streams[stream_index]->codec->codec->capabilities &
                CODEC_CAP_DELAY))
        return 0;
    while (1) {
        av_log(NULL, AV_LOG_INFO, "Flushing stream #%u encoder\n", stream_index);
        //ret = encode_write_frame(NULL, stream_index, &got_frame);
        enc_pkt.data = http://www.mamicode.com/NULL;>

结果

程序运行的结果如下图所示。


转码前的视频信息使用MediaInfo查看如下图所示。


转码后的视频信息使用MediaInfo查看如下图所示。


下载 

SourceForge项目主页:

https://sourceforge.net/projects/simplestffmpegmemhandler/


CSDN项目下载地址:
http://download.csdn.net/detail/leixiaohua1020/8003731


注:
 本工程包含两个FFmpeg读写内存的例子:
 simplest_ffmpeg_mem_player:基于FFmpeg的内存播放器。
 simplest_ffmpeg_mem_transcoder:基于FFmpeg的内存转码器。

 

最简单的基于FFmpeg的内存读写的例子:内存转码器