AVCodec是ffmpeg设计上的一个结构体,用来保存编解码器的信息。

小白:都有哪些信息呢?还有,能不能直观一点让我看到具体的数值?

本文写一个简单的demo,并调试查看avcodec变量中的内容。

(1)demo代码

演示代码的目录结构是这样的:

FFmpeg之AVCodec_java

其中的ffmpeg静态库是事先编译好的(这里是macos版本),编译的办法可以参考之前的文章,之前有详细介绍过编译的环节。

moments.mp4 是试用的视频文件(mp4封装格式,之前也有介绍过哦!)。

makefile是编译脚本,当然也可以直接用gcc来编译。

小白:为什么西门吹雪还没有找我,他到底还想不想讲编译工具的使用了!

show_avcodec.c就是演示代码了,内容如下:

#include "libavcodec/avcodec.h"

#include "libavformat/avformat.h"


void show_avcodec(const char* filepath) {

av_register_all();

av_log_set_level(AV_LOG_DEBUG);

AVFormatContext* formatContext = avformat_alloc_context();

int status = 0;

int success = 0;

int videostreamidx = -1;

AVCodecContext* codecContext = NULL;

status = avformat_open_input(&formatContext, filepath, NULL, NULL);

if (status == 0) {

status = avformat_find_stream_info(formatContext, NULL);

if (status >= 0) {

for (int i = 0; i < formatContext->nb_streams; i ++) {

if (formatContext->streams[i]->codec->codec_type == AVMEDIA_TYPE_VIDEO) {

videostreamidx = i;

break;

}

}

if (videostreamidx > -1) {

codecContext = formatContext->streams[videostreamidx]->codec;

AVCodec* codec = avcodec_find_decoder(codecContext->codec_id);

if (codec) {

status = avcodec_open2(codecContext, codec, NULL);

if (status == 0) {

success = 1;

}

}

}

}

else {

av_log(NULL, AV_LOG_DEBUG, "avformat_find_stream_info error\n");

}

avformat_close_input(&formatContext);

}

avformat_free_context(formatContext);

}


int main(int argc, char *argv[])

{

show_avcodec("moments.mp4");

return 0;

}


(2)编译与调试

makefile的内容:

exe=showavcodec

srcs=show_avcodec.c 

$(exe):$(srcs)

gcc -o $(exe) $(srcs) -Iffmpeg/include/ -Lffmpeg -lffmpeg -liconv -lz -g

clean:

rm -f $(exe) *.o


直接执行make来编译。

这里只是简单看一下avcodec的内容,所以用gdb来调试即可:

gdb showavcodec
b 25
r


在断点的地方,看一下avcodec变量中的值: 

FFmpeg之AVCodec_java_02

(3)avcodec是什么?

编解码器的结构体,在libavcodec/avcodec.h中定义。

在这个示例中,是一个解码器。

avcodec结构中的一些变量,从名字或Ffmpeg详细的注释可以知道是什么含义。

比如name是编解码的名称,而long_name就是长的名称,等等。

在设计上,avcodec是编解码器的抽象,那么就有具体的实现。事实上,每一个编解码器都有具体的实现。

比如h264的解码器(libavcodec/h264.c): 
FFmpeg之AVCodec_java_03

比如mp3lame的编码器(libavcodec/libmp3lame.c) 
FFmpeg之AVCodec_java_04

小白:也就是说,我可以直接使用这些具体的全局变量了?

花满楼:是的,是FFmpeg可以直接使用。

https://mp.weixin.qq.com/s/5Q8w5DOaa1lqygNfq4Zm3w