在海思3519上基于qt采用ffmpeg对avi进行解码显示,其中ffmpeg的配置,qt的配置在前文中已经说明,在此不再赘述。

解码

解码在单独的线程中进行,具体的代码如下:

void VideoPlayer::run()
{
AVFormatContext *fmt_ctx = NULL;
AVCodecContext *dec_ctx = NULL;
AVFrame *pf = av_frame_alloc();
AVFrame *pfc = av_frame_alloc();
int video_stream_index;
int width, height;
av_register_all(); video_stream_index = getStream(&fmt_ctx, &dec_ctx, "./source_file/test.avi"); decoder(&fmt_ctx, &dec_ctx, video_stream_index, pf, pfc, &width, &height);
} int VideoPlayer::decoder(AVFormatContext** fmt_ctx, AVCodecContext** dec_ctx,
int video_stream_index, AVFrame *pFrame, AVFrame *pFrameColor, int* width, int* height)
{
AVPacket packet;
int i = 0;
int frameFinished;
uint8_t *buffer;
int numBytes;
char filename[32]; numBytes = avpicture_get_size(AV_PIX_FMT_RGB24, (*dec_ctx)->width, (*dec_ctx)->height);
buffer = (uint8_t*)av_malloc(numBytes);
avpicture_fill((AVPicture *)pFrameColor, buffer, AV_PIX_FMT_RGB24, (*dec_ctx)->width, (*dec_ctx)->height); while (av_read_frame(*fmt_ctx, &packet) >= 0) {
if (packet.stream_index == video_stream_index) {
avcodec_decode_video2(*dec_ctx, pFrame, &frameFinished, &packet);
if (frameFinished)
{ struct SwsContext *img_convert_ctx = NULL;
img_convert_ctx = sws_getCachedContext(img_convert_ctx, (*dec_ctx)->width,
(*dec_ctx)->height, (*dec_ctx)->pix_fmt,
(*dec_ctx)->width, (*dec_ctx)->height,
AV_PIX_FMT_RGB24, SWS_BICUBIC,
NULL, NULL, NULL);
if (!img_convert_ctx) {
fprintf(stderr, "Cannot initialize sws conversion context\n");
exit(1);
} sws_scale(img_convert_ctx, (const uint8_t* const*)pFrame->data,
pFrame->linesize, 0, (*dec_ctx)->height, pFrameColor->data,
pFrameColor->linesize); QImage tmpImg((uchar *)buffer,(*dec_ctx)->width,(*dec_ctx)->height,QImage::Format_RGB888);
QImage image = tmpImg.copy();
emit sig_GetOneFrame(image); }
}
av_free_packet(&packet);
}
printf("finished"); av_free(buffer);
av_free(pFrameColor);
av_free(pFrame);
avcodec_close(*dec_ctx);
avformat_close_input(fmt_ctx);
} int VideoPlayer::getStream(AVFormatContext **fmt_ctx, AVCodecContext **dec_ctx, char* file_name)
{
int video_stream_index = -1;
int ret;
bool decoder_init = false; if ((ret = avformat_open_input(fmt_ctx, file_name, NULL, NULL)) < 0) {
av_log(NULL, AV_LOG_ERROR, "fail to open input file.\n");
return ret;
} if ((ret = avformat_find_stream_info(*fmt_ctx, NULL)) < 0) {
av_log(NULL, AV_LOG_ERROR, "fail to find stream information.\n");
avformat_close_input(fmt_ctx);
return ret;
} for (int i = 0; i < (*fmt_ctx)->nb_streams; i++) {
if ((*fmt_ctx)->streams[i]->codec->codec_type == AVMEDIA_TYPE_VIDEO) {
video_stream_index = i; if (!decoder_init) {
*dec_ctx = (*fmt_ctx)->streams[i]->codec; AVCodec *cod = avcodec_find_decoder((*dec_ctx)->codec_id); if (!cod) {
av_log(NULL, AV_LOG_ERROR, "fail to find decoder.\n");
avformat_close_input(fmt_ctx);
return 1;
}
if (avcodec_open2(*dec_ctx, cod, NULL) != 0) {
av_log(NULL, AV_LOG_ERROR, "fail to open codecer.\n");
avformat_close_input(fmt_ctx);
return 2;
}
decoder_init = true; }
}
return 0;
} return video_stream_index;
}

解码后将数据转换成RGB并进一步转换成QImage,每解码一帧数据后发送一个信号用于更新图像显示

QImage tmpImg((uchar *)buffer,(*dec_ctx)->width,(*dec_ctx)->height,QImage::Format_RGB888);
QImage image = tmpImg.copy();
emit sig_GetOneFrame(image);

显示

具体代码如下:


void MainWindow::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setBrush(Qt::black);
painter.drawRect(0, 0, this->width(), this->height()); //先画成黑色 if (mImage.size().width() <= 0) return; QImage img = mImage.scaled(this->size(),Qt::KeepAspectRatio); int x = this->width() - img.width();
int y = this->height() - img.height(); x /= 2;
y /= 2; painter.drawImage(QPoint(x,y),img); //画出图像 } void MainWindow::slotGetOneFrame(QImage img)
{
mImage = img;
update();
}

总结:

编译后能够在板子上成功运行,但是显示比较缓慢,这块具体的原因没有进一步分析,因为后来才用了硬解码的方式,所以放弃了深入研究,参考代码获取

海思3519 qt ffmpeg 软解码播放avi的更多相关文章

  1. 海思3559A QT 5.12移植(带webengine 和 opengl es)

    海思SDK版本:Hi3559AV100_SDK_V2.0.1.0 编译器版本:aarch64-himix100-linux-gcc 6.3.0(这个版本有点小问题,使用前需要先清除本地化设置) $ e ...

  2. 海思3519A 移植ffmpeg

    文件下载 下载x264 git clone git://git.videolan.org/x264.git 下载ffmpeg git clone git://source.ffmpeg.org/ffm ...

  3. Qt + FFmpeg 本地音频播放器

    http://pan.baidu.com/s/1hqoYXrI

  4. FFmpeg开发笔记(十):ffmpeg在ubuntu上的交叉编译移植到海思HI35xx平台

    FFmpeg和SDL开发专栏(点击传送门) 上一篇:<FFmpeg开发笔记(九):ffmpeg解码rtsp流并使用SDL同步播放>下一篇:敬请期待   前言   将ffmpeg移植到海思H ...

  5. OpenCV开发笔记(七十四):OpenCV3.4.1+ffmpeg3.4.8交叉编译移植到海思平台Hi35xx平台

    前言   移植opencv到海思平台,opencv支持对视频进行解码,需要对应的ffmpeg支持.   Ffmpeg的移植   Ffmpeg的移植请参考之前的文章:<FFmpeg开发笔记(十): ...

  6. (转)海思平台HI35XX系列内存设置

    海思平台的内存分为两部分,一部分给系统使用,另外的一部分给多媒体使用.可以通过cat /proc/meminfo查看系统内存和cat /proc/media-mem 查看多媒体内存使用情况. /pro ...

  7. 海思3519A 移植 Qt 5.5.1

    源码下载 网址:qt-everywhere-opensource-src-5.5.1.tar.gz 配置生成MakeFile 文件 解压源码包,在源码包路径下生成配置 MakeFile : ./con ...

  8. 使用C#+FFmpeg+DirectX+dxva2硬件解码播放h264流

    本文门槛较高,因此行文看起来会乱一些,如果你看到某处能会心一笑请马上联系我开始摆龙门阵 如果你跟随这篇文章实现了播放器,那你会得到一个高效率,低cpu占用(单路720p视频解码播放占用1%左右cpu) ...

  9. 海思HI35xx平台软件开发快速入门之H264解码实例学习

    ref :https://blog.csdn.net/wytzsjzly/article/details/82500277   前言 H264视频编码技术诞生于2003年,至今已有十余载,技术相当成熟 ...

随机推荐

  1. 使用ES6 Class封装的IndexDB 操作类,并实现模糊搜索

     封装如下: indexDBOperate.js export class IndexDBOperate { db = null // 数据库实例 databaseName = null // 数据库 ...

  2. bcc 基于bpf 分析linux 系统性能的强大工具包

    bcc 是一个基于bpf 的强大linux io,网络监控分析工具集(当然也可以分析java,ruby,python...) 一张工具图 说明 bcc 好多工具是需要kernel 4.1 的,但是大部 ...

  3. github新建本地仓库并将代码提交到远程仓库

    方式一: 在github上新建好仓库:gitTest 使用命令git clone git@github.com:yourgithubID/gitTest.git,克隆到本地相应的位置 将要上传的工程代 ...

  4. [转]细说OpenSessionInView问题

    转载:https://www.cnblogs.com/zjrodger/p/4615809.html. [环境参数] 环境:SSH框架 [问题描述]  NoSession问题 HibernateTem ...

  5. [学习笔记] 网络最大流的HLPP算法

    #define \(u\)的伴点集合 与\(u\)相隔一条边的且\(u\)能达到的点的集合 \(0x00~ {}~Preface\) \(HLPP(Highest~Label~Preflow~Push ...

  6. Codeforces 652F 解题报告

    题意 有n只蚂蚁在长度为m个格子的环上,环上的格子以逆时针编号,每只蚂蚁每秒往它面向的方向移动一格.如果有两只蚂蚁相撞则相互调换方向,问t秒后每只蚂蚁的位置. 题解 首先通过观察可以发现 蚂蚁相撞产生 ...

  7. thinkphp5.1 - twig模板-全局变量

    thinkphp5.1 - twig模板-全局变量我们在定义 ccs 之类的静态文件的时候,经常会使用<link rel="stylesheet" href="__ ...

  8. AtCoder Grand Contest 035 简要题解

    从这里开始 题目目录 Problem A XOR Circle 你发现,权值的循环节为 $a_0, a_1, a_0\oplus a_1$,然后暴力即可. Code #include <bits ...

  9. vue组件component没效果

    如果实在不知道问题所在,你就看看你的component的命名是不是驼峰命名

  10. kibana无法显示elasticsearch中的index

    我是用的logstash将kafka中的数据同步到elasticsearch.logstash和kafka在同一台服务器,elasticsearch在另外的服务器上. 经过排查,是因为我的logsta ...