QT开发用ffmpeg将图片制作成视频
继上一博文:QT打开图片文件夹快速播放图片现在要将图片做成视频
1,第一种方式:cmd 的调用:因为什么都不懂,刚开始是想用命令行来做,在cmd下用命令能合成比较模糊的视频了
因输入文件的方式有两种调用方式:
第一种:ffmpeg -f image2 -pattern_type glob -framerate 24 -i 'IMG_*.JPG' ./IMG_.avi
第二种:ffmpeg -f image2 -r 1/5 -i img%03d.png -vcodec libx264 -pix_fmt yuv420p out.mp4
第二种方式要求输入图片文件名要有规则,如:%03d 代表 001 开始 如:%04d 代表 0001开始
我的文件的命名是 IMG_0152.JPG IMG_0220.JPG IMG_0288.JPG ...... 因此用第一种方式,第一种方式的输出文件名必是IMG_与文件名一样,而且不知为什么,当改成mp4时就生成不了视频了。
参考:http://ffmpeg.org/ffmpeg.html https://stackoverflow.com/questions/21586256/turning-images-into-videos-with-ffmpeg
接下来是在代码中调用了,最后不知什么原因运行不起来ffmpeg,不知哪里不对,真是小白,代码还是上来吧:
QString inputFiles = srcDir + "/IMG_0660.JPG";
QString outputFile = "/Users/ljx/IMG_.avi";
QString cmd = "ffmpeg";///usr/loacl/ffmpeg.app";
//QString cmd = "ffmpeg -f image2 -pattern_type glob -framerate 18 -i "+inputFiles + " " + outputFile;
qDebug() << "on_createAviBtn_clicked inputFiles:"<< inputFiles << " out:" <<outputFile;
QStringList arguments;
// //arguments.append("ffmpeg");
// arguments.append("-f");
// arguments.append("image2");
// arguments.append("-pattern_type");
// arguments.append("glob");
// arguments.append("-framerate");
// arguments.append("18");
// arguments.append("-i");
// arguments.append(inputFiles);
// arguments.append(" ");
// arguments.append(outputFile);
arguments.append("-version");
QProcess *p = new QProcess(this);
int in = p->execute(cmd,arguments);
//p.start(cmd,arguments);
bool b = p->waitForStarted();
bool b2 = p->waitForFinished();//等待完成
QString strTemp=QString::fromLocal8Bit(p->readAllStandardOutput());
qDebug() << "QProcess finished in: "<< in <<" b:"<< b + " b2:"<<b2 << " strTemp:" << strTemp;
2. 第二种方式:用代码调用ffmpeg函数,下面这个终于能生成一个图片的视频了,有些参数还不太正,但原型出来了,相信再改动,就ok 了
void VideoMaker::makeVideo(QStringList srcList,QString desFile)
{
if(srcList.size()<=0){
return;
}
qDebug() << "........-> makeVedio";
av_register_all();//初始化解码器和复用器
const char *out_filename = "/Users/ljx/maked.mp4";
qDebug() << "-------------------AVFormatContext oc 1";
AVFormatContext* oc = NULL;//其包含码流参数较多,是一个贯穿始终的数据结构,很多函数都要用到它作为参数
//首先创建一个封装格式,
avformat_alloc_output_context2(&oc, NULL, NULL,out_filename);//初始化一个用于输出的AVFormatContext结构体,视频帧率和宽高在此函数里面设置
if(!oc)
{
qDebug() << "-------------------AVFormatContext oc init failed";
return;
}
oc->oformat->video_codec = AV_CODEC_ID_MJPEG;
qDebug() << "-------------------AVStream st 2";
AVStream *st;//构造一个输出流
st = avformat_new_stream(oc, NULL);//初始化输出流
if(!st)
{
av_free(oc);
qDebug() << "-------------------AVStream st init failed";
return;
}
qDebug() << "-------------------AVCodecContext c 3";
AVCodecContext *c;
av_dump_format(oc,0,out_filename,1);//一个打印的函数,应该没用
c = st->codec;
// c->codec_id = oc->oformat->video_codec;
// c->codec_type = AVMEDIA_TYPE_VIDEO;
// c->bit_rate = 400000;
// c->width = 640;
// c->height = 360;
// c->time_base.den = 12;
// c->time_base.num =1;
// c->gop_size = 12;
// c->pix_fmt = AV_PIX_FMT_YUV420P;
// c->flags |= CODEC_FLAG_GLOBAL_HEADER;
// c->codec_tag = 0;
qDebug() << "-------------------AVCodec codec 4";
AVCodec *codec;
codec = avcodec_find_encoder(AV_CODEC_ID_MJPEG);//查找mjpeg解码器
if (!codec)
{
av_free(oc);
qDebug() << "-------------------AVCodec codec init failed";
return;
}
qDebug() << "-------------------avcodec_get_context_defaults3 5";
avcodec_get_context_defaults3(st->codec, codec);//申请AVStream->codec(AVCodecContext对象)空间并设置默认值(由avcodec_get_context_defaults3()设置
//avcodec_get_context_defaults3(c,codec);
avcodec_open2(c,codec,NULL);
avcodec_parameters_from_context(st->codecpar,c);
AVCodecParameters *codecpar = st->codecpar;
codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
codecpar->bit_rate = 400000;//设置采样参数,即比特率
codecpar->width = 640;//设置视频宽高,这里跟图片的宽高保存一致即可
codecpar->height = 360;
//codecpar->format = 12;
st->time_base.den = 25;//设置帧率
st->time_base.num = 1;
st->codec->gop_size = 12;
st->codec->pix_fmt = AV_PIX_FMT_YUV420P;//设置像素格式
st->codec->codec_tag = 0;
if (oc->oformat->flags & AVFMT_GLOBALHEADER)//一些格式需要视频流数据头分开
{
qDebug() << "-------------------if (oc->oformat->flags & AVFMT_GLOBALHEADER) ";
st->codec->flags |= CODEC_FLAG_GLOBAL_HEADER;
}
if (!(oc->oformat->flags & AVFMT_NOFILE))//打开输出视频文件
{
int ret = avio_open(&oc->pb, out_filename, AVIO_FLAG_WRITE);
if (ret < 0) {
av_free(oc);
printf("Could not open output file '%s'", out_filename);
return;
}
qDebug() << "-------------------if (!(oc->oformat->flags & AVFMT_NOFILE)) ";
}
if (avformat_write_header(oc, NULL) < 0)//写文件头(Write file header)
{
printf("Error occurred when opening output file\n");
return;
}
qDebug() << "------------------open file 6";
QFile file(srcList.at(0));
if (!file.open(QIODevice::ReadOnly))
{
printf("Error occurred when opening jpg file\n");
return;
}
QByteArray arr = file.readAll();
//char* p = arr.data();
uint8_t *mydata = (uint8_t*)arr.data();
qDebug() << "-------------------arr.len:"<< arr.length() << " file.size:" << file.size() << " 1024 * 521:" << 1024*512;
//QDataStream in(&file);
//in.readBytes(mydata,file.size());
//QTextStream in(&file);
//打开一张jpeg图像并读取其数据,在这里图像最大为1M,如果超过1M,则需要修改1024*1024这里
AVPacket *pkt = av_packet_alloc();
qDebug() << "------------------av_interleaved_write_frame 7";
pkt->data = mydata;
pkt->size = file.size();
//fclose(file);
qDebug() << "------------------av_interleaved_write_frame 8";
if (av_interleaved_write_frame(oc, pkt) < 0) //写入图像到视频
{
printf("Error muxing packet\n");
return;
}
file.close();
//这个地方读取图片可以直接替换成其他内存,但是图片编码格式要一致,这里是yuv
qDebug() << "------------------free 9";
av_free_packet(pkt);//释放掉帧数据包对象
av_write_trailer(oc);//写文件尾(Write file trailer)
delete mydata;//释放数据对象
if (oc && !(oc->oformat->flags & AVFMT_NOFILE))
avio_close(oc->pb);//关闭视频文件
avformat_free_context(oc);//释放输出视频相关数据结构
}
上面过程中的问题:
问题一:
- Using AVStream.codec to pass codec "
- "parameters to muxers is deprecated, use AVStream.codecpar "
- "instead.
要设置codec_type
codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
参考:http://blog.csdn.net/yibu_refresh/article/details/52882925
问题二:读取图片成 uint8_t* : 原来char* 可以强制转成 uint8_t*
QFile file(“文件路径”);
if (!file.open(QIODevice::ReadOnly))
{
printf("Error occurred when opening jpg file\n");
return;
}
QByteArray arr = file.readAll();
//char* p = arr.data();
uint8_t *mydata = (uint8_t*)arr.data();
问题三: Could not find tag for codec none in stream #0, codec not currently supported in container” 在avcodec_open2 成功之后,利用avcodec_parameters_from_context将编码器的参数赋值给AVStream中的codecpar字段,问题解决
参考:http://blog.csdn.net/zhuquanfu/article/details/53786759
合成视频参考 http://www.zzzyk.com/show/7f3ead2a4a429116.htm
ffmpeg的c代码官方示例(在安装路径如:/usr/loacl/share/ffmpeg/examples下也有):
https://github.com/FFmpeg/FFmpeg/tree/master/doc/examples
QT程序发布:http://blog.csdn.net/liuyez123/article/details/50462637
QT开发用ffmpeg将图片制作成视频相关推荐
- matlab把图片制作成视频
matlab把图片制作成视频 file_path = 'F:\数据\cqq\融合\11-08tig钛合金\16-47\低曝光';img_path_list = dir(strcat(file_path ...
- matlab 将图片制作成视频并将视频输出为图片
matlab 2016 videowriter制作视频 matlab在2013版之前制作视频有avifile以及addframe函数可以使用,但在之后的版本中这两个函数已经被移除,取而代之的是Vide ...
- 流媒体服务器开发——SRS 4.0与WebRTC音视频通话丨音视频开发丨嵌入式开发丨FFmpeg丨iOS音视频开发
SRS 4.0与WebRTC音视频通话 1. 音视频高薪岗位都需要什么技能点 2. WebRTC的技术点分析 3. SRS 4.0如何使用WebRTC 视频讲解如下,点击观看: 流媒体服务器开发--S ...
- ImageMagick将多张图片拼接成一张图片_爱剪辑如何把图片制作成视频
爱剪辑是视频剪辑里很较常用到的一款软件,我也不少次向初学者们分享这个软件,现在就各自简易讲解一下用电脑版本和手机版本2个版本的爱剪辑该怎么制作你们美好的图片视頻. 一.电脑版本爱剪辑如何把图片制作成视 ...
- 怎样在php中制作电子相册,制作电子相册 如何将图片制作成视频并配上合适的音乐?电脑制作电子相册的方法...
现在很多的朋友都喜欢将照片制作成视频,这样就可以发送到朋友圈啦~那么如何电脑制作电子相册呢?就是电脑怎么制作电子相册?此教程不是3d电子相册制作教程,而是将电脑本地的图片制作成电子相册哦.操作很简单, ...
- 用Qt开发的ffmpeg流媒体播放器,支持截图、录像,支持音视频播放,支持本地文件播放、网络流播放
前言 本工程qt用的版本是5.8-32位,ffmpeg用的版本是较新的5.1版本.它支持TCP或UDP方式拉取实时流,实时流我采用的是监控摄像头的RTSP流.音频播放采用的是QAudioOutput, ...
- Qt实现 基于ffmpeg拉流播放视频
1.前言 ffmpeg作为开源库,具备跨平台性,被广泛使用于各大视频软件和网站,在视音频开发中占有极其重要的地位. Qt同样支持跨平台,因此结合qt+ffmpeg制作跨平台视频播放器是比较合适的做法. ...
- QT开发实践之简单的图像视频处理软件
引言 这学期学习了QT桌面应用程序开发基础,实践课我选择做了一个简单的图像图像视频处理软件(灰度化.边缘检测等等),其中视频的读取我是选用了摄像头的读取(方便). 效果图 主界面 处理效果 ...
- 【Qt学习】 FFmpeg 解码播放本地视频
目录 一:效果展示 二:源码分享 一:效果展示 二:源码分享 videodecode.h .cpp [解码线程的封装] #ifndef VIDEODECODE_H #define VIDEODECOD ...
最新文章
- 密码技术--国密证书及go语言生成自签国密证书
- Newlife.Net QA
- 网络编程—网络基础概览、socket,TCP/UDP协议
- Angular structural指令host element的定位调试
- android Module之间数据传递
- VBoxManage: error: Nonexistent host networking interface, name 'vboxnet0' (VERR_INTERNAL_ERROR)
- python截取指定字符串_python 正则匹配获取指定多个词的在字符串(句子/段落)索引位置...
- python crypto安装_关于python安装pip及crypto库
- 用.htaccess 禁止IP访问
- python 关于main函数以及if __name__=='__main__'的理解
- JAVA内存管理+String创建字符串对象+常量池详解(合集)
- 计算机键盘重复设置,教你操作win10系统电脑键盘打字时总是出现重复字符的方案...
- 移动端百度点击软件操作方法及常见问题
- Excel表格中选择性粘贴如何粘贴为数值
- 从程序员到项目经理(六):程序员加油站 — 懂电脑更要懂人脑
- C语言基础 判断周几
- 计算机期刊杂志投稿指南
- 行业前研|人工智能在作战仿真中的应用
- AE C# 图片标注背景透明
- EXCEL 也可以使用chatGPT了,教程来了