ffmpeg入——安装
Fmpeg地址
FFmpeg源码地址:https://github.com/FFmpeg/FFmpeg
FFmpeg可执行文件地址:https://ffmpeg.org/download.html
Windows平台
Windows平台下载解压后如图所示(文件名称以-share结尾的是开发库)
FFmpeg库介绍
◆ ffmpeg.exe:用于音视频转码, 也可以从url/现场音频/视频源抓取输入源。
◆ ffplay.exe:一个非常简单和可移植的媒体播放器,使用FFmpeg库和SDL库。
◆ ffprobe.exe:查看多媒体文件的信息
将FFmpeg可执行文件加入系统环境变量,如下图所示:
Linux
ffmpeg官方 GitHub - FFmpeg/FFmpeg: Mirror of https://git.ffmpeg.org/ffmpeg.git
下载压缩包 或者 直接clone
- 直接clone:git clone https://github.com/FFmpeg/FFmpeg.git
- 下载完成,执行./configure
如果出现了错误 nasm/yasm not found or too old. Use --disable-x86asm for a crippled build.
。
这是因为 FFMPEG为了提高编译速度,使用了汇编指令,如MMX和SSE等。如果系统中没有yasm
指令的话,就会该错误。
1)下载:wget http://www.tortall.net/projects/yasm/releases/yasm-1.3.0.tar.gz
2)解压:tar zxvf yasm-1.3.0.tar.gz
3)切换路径: cd yasm-1.3.0
4)执行配置: ./configure
5)编译:make
6)安装:make install
3.make && sudo make install
测试代码:
#include<stdio.h>
#include<libavutil/log.h>
int main()
{
av_log_set_level(AV_LOG_DEBUG); //设置日志等级
av_log(NULL, AV_LOG_INFO, "Hello~~~\n"); // INFO等级,输出hello
return 0;
}
编译链接: gcc -o ff_log ff_log.c -lavutil
或者 gcc -o ff_log ff_log.c `pkg-config --cflags --libs libavutil`
(“pkg-config工具:1)会检查库的版本号。如果所需要的库的版本不满足要求,它会打印出错误信息,避免链接错误版本的库文件;2)会获得编译预处理参数,如宏定义,头文件的位置。3)还会获得链接参数,如库及依赖的其它库的位置,文件名及其它一些连接参数)
选项--cflags 它是用来指定程序在编译时所需要头文件所在的目录, 选项 --libs则是指定程序在链接时所需要的动态链接库的目录。
ffmpeg——log日志系统
log日志位于libavutil模块,log level的声明位于log.h
日志级别:
// 静默模式,不打印日志
#define AV_LOG_QUIET -8
// 立即崩溃,退出程序
#define AV_LOG_PANIC 0
// 严重出错,无法修复
#define AV_LOG_FATAL 8
// 程序出错
#define AV_LOG_ERROR 16
// 警告
#define AV_LOG_WARNING 24
// 信息
#define AV_LOG_INFO 32
// 详细信息
#define AV_LOG_VERBOSE 40
// 调试日志
#define AV_LOG_DEBUG 48
// 跟踪日志
#define AV_LOG_TRACE 56
设置日志等级的方法set_log_level()位于log.c,其中av_log_level是个静态全局变量,具体如下
static int av_log_level = AV_LOG_INFO;
void av_log_set_level(int level)
{
av_log_level = level;
}
常用的打印日志方法av_log(),声明位于log.h:
/**
* 发送特定消息到小于等于当前等级的日志,默认全部发送到stderr
*
* @param avcl 指向任意结构体的指针,结构体第一个变量为AVClass或NULL
* @param level 日志等级
* @param fmt 字符串格式
*/
void av_log(void *avcl, int level, const char *fmt, ...) av_printf_format(3, 4);
ffmpeg——文件的删除与重命名
- avpriv_io_delete() //删除
- avpriv_io_move() //重命名
编译链接: gcc xxx.c -o xxx -lavformat -lavutil
#include <libavformat/avformat.h>
int main(int argc,char *argv[])
{
int ret;
set_av_log_level(AV_LOG_DEBUG);
ret = avpriv_io_move("111.txt","222.txt");
if(ret < 0)
{
av_log(NULL,AV_LOG_ERROR,"Failed to move file:%s\n","111.txt");
return -1;
}
ret = avpriv_io_delete("./mytestfile.txt");
if(ret < 0)
{
av_log(NULL,AV_LOG_ERROR,"Failed to delete file:%s\n","mytestfile.txt");
return -1;
}
av_log(NULL,AV_LOG_DEBUG,"Success to delete file:%s\n","mytestfile.txt");
return 0;
}
ffmpeg——目录操作
重要结构体:
AVIODirContext 操作目录的上下文(记录avio_open_dir打开目录信息)
AVIODirEntry 目录项。用于存放文件名,文件大小等信息
操作目录API:
- avio_open_dir()
- avio_read_dir()//读取目录中每一个文件的属性
- avio_close_dir()
编译链接: gcc xxx.c -o xxx -lavformat -lavutil
// 实现简单的ls命令
#include <libavutil/log.h>
#include <libavformat/avformat.h>
int main(int argc,char* argv[])
{
int ret;
AVIODirContext *ctx = NULL;
AVIODirEntry *entry = NULL;
av_log_set_level(AV_LOG_INFO);
ret = avio_open_dir(&ctx,"./",NULL);
if(ret < 0){
av_log(NULL,AV_LOG_ERROR,"Cant open dir:%s\n",av_err2str(ret));
return -1;
}
while(1){
ret = avio_read_dir(ctx,&entry);//malloc entry
if(ret < 0){
av_log(NULL,AV_LOG_ERROR,"Cant read dir:%s\n",av_err2str(ret));
avio_close_dir(&ctx);
return -1;
}
if(!entry){
//the end
break;
}
av_log(NULL,AV_LOG_INFO,"%12"PRId64" %s\n",
entry->size,
entry->name);
avio_free_directory_entry(&entry);//free entry
}
avio_close_dir(&ctx);
return 0;
}
ffmpeg——多媒体文件
多媒体文件是一个容器(也可以理解为包装盒,常见的mp4、flv、mkv都是不同的包装盒 ),可以存放很多数据,最常见的有字幕数据、视频数据、音频数据。
在容器中有很多流(Stream/Track),流媒体文件中不同的流之数据不会相交的,比如音频流和视频流就是各自独立的。
每种流是由不同的编码器编码的,每条流数据在多媒体文件中是经过压缩的,但是其使用压缩的编码器都是不一样的。比如音频有可能是MP3,有可能是AAC,视频常见的压缩器有可能是H264或者H265。
从流中读出的数据称为包,在一个包中包含着一个或者多个帧。
重要的结构体
- AVFormatContext //格式上下文(记录打开多媒体文件的信息,多个API桥梁作用)
- AVStream // 流
- AVPacket // 包