FFmpeg中编码类型为rawvideo无须解码直接显示测试代码

2023-10-30

在 https://blog.csdn.net/fengbingchun/article/details/93975325 中介绍过通过FFmpeg可以直接获取usb视频流并解码显示的测试代码,当时通过usb获取到的视频流编码类型为AV_CODEC_ID_RAWVIDEO,像素格式为AV_PIX_FMT_YUYV422,其实编码类型为rawvideo的视频流可以不经过解码操作直接就可进行显示,测试代码如下:

#include "funset.hpp"
#include <stdio.h>
#include <iostream>
#include <memory>
#include <fstream>

#ifdef __cplusplus
extern "C" {
#endif

#include <libavdevice/avdevice.h>
#include <libavformat/avformat.h>
#include <libavcodec/avcodec.h>
#include <libswscale/swscale.h>
#include <libavutil/mem.h>
#include <libavutil/imgutils.h>

#ifdef __cplusplus
}
#endif

#include <opencv2/opencv.hpp>

int test_ffmpeg_stream_show()
{
	avdevice_register_all();

#ifndef _MSC_VER
	const char* input_format_name = "video4linux2";
	const char* url = "/dev/video0";

	AVInputFormat* input_fmt = av_find_input_format(input_format_name);
	AVFormatContext* format_ctx = avformat_alloc_context();

	int ret = avformat_open_input(&format_ctx, url, input_fmt, nullptr);
	if (ret != 0) {
		fprintf(stderr, "fail to open url: %s, return value: %d\n", url, ret);
		return -1;
	}

	ret = avformat_find_stream_info(format_ctx, nullptr);
	if (ret < 0) {
		fprintf(stderr, "fail to get stream information: %d\n", ret);
		return -1;
	}

	int video_stream_index = -1;
	for (unsigned int i = 0; i < format_ctx->nb_streams; ++i) {
		const AVStream* stream = format_ctx->streams[i];
		if (stream->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
			video_stream_index = i;
			fprintf(stdout, "type of the encoded data: %d, dimensions of the video frame in pixels: width: %d, height: %d, pixel format: %d\n",
				stream->codecpar->codec_id, stream->codecpar->width, stream->codecpar->height, stream->codecpar->format);
		}
	}

	if (video_stream_index == -1) {
		fprintf(stderr, "no video stream\n");
		return -1;
	}

	AVCodecParameters* codecpar = format_ctx->streams[video_stream_index]->codecpar;
	const AVCodec* codec = avcodec_find_decoder(codecpar->codec_id);
	if (!codec) {
		fprintf(stderr, "fail to avcodec_find_decoder\n");
		return -1;
	}

	AVCodecContext* codec_ctx = avcodec_alloc_context3(codec);
	if (!codec_ctx) {
		fprintf(stderr, "fail to avcodec_alloc_context3\n");
		return -1;
	}

	codec_ctx->pix_fmt = AVPixelFormat(codecpar->format);
	codec_ctx->height = codecpar->height;
	codec_ctx->width = codecpar->width;
	codec_ctx->thread_count = 16;
	ret = avcodec_open2(codec_ctx, codec, nullptr);
	if (ret != 0) {
		fprintf(stderr, "fail to avcodec_open2: %d\n", ret);
		return -1;
	}

	AVPacket* packet = (AVPacket*)av_malloc(sizeof(AVPacket));
	SwsContext* sws_ctx = sws_getContext(codec_ctx->width, codec_ctx->height, codec_ctx->pix_fmt, codec_ctx->width, codec_ctx->height, AV_PIX_FMT_BGR24, 0, nullptr, nullptr, nullptr);
	if (!packet || !sws_ctx) {
		fprintf(stderr, "fail to alloc\n");
		return -1;
	}

	uint8_t *bgr_data[4], *yuyv422_data[4];
	int bgr_linesize[4], yuyv422_linesize[4];
	av_image_alloc(bgr_data, bgr_linesize, codec_ctx->width, codec_ctx->height, AV_PIX_FMT_BGR24, 1);
	av_image_alloc(yuyv422_data, yuyv422_linesize, codec_ctx->width, codec_ctx->height, AV_PIX_FMT_YUYV422, 1);
	cv::Mat mat(codec_ctx->height, codec_ctx->width, CV_8UC3);
	const char* winname = "usb video";
	cv::namedWindow(winname);
	const uint8_t *srcSlice[1];

	while (1) {
		ret = av_read_frame(format_ctx, packet);
		if (ret >= 0 && packet->stream_index == video_stream_index) {
			srcSlice[0] = packet->data;
			sws_scale(sws_ctx, srcSlice, yuyv422_linesize, 0, codec_ctx->height, bgr_data, bgr_linesize);
			mat.data = bgr_data[0];
			cv::imshow(winname, mat);
		}

		av_packet_unref(packet);

		int key = cv::waitKey(25);
		if (key == 27) break;
	}

	cv::destroyWindow(winname);
	sws_freeContext(sws_ctx);
	avformat_close_input(&format_ctx);
	av_freep(packet);
	av_freep(&bgr_data[0]);
	av_freep(&yuyv422_data[0]);

	fprintf(stdout, "test finish\n");

	return 0;
#else
	fprintf(stderr, "Error: this interface only support usb camera: encode type: rawvideo\n");
	return -1;
#endif
}

执行结果如下:

GitHubhttps://github.com//fengbingchun/OpenCV_Test

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

FFmpeg中编码类型为rawvideo无须解码直接显示测试代码 的相关文章

  • Email Error - You have exceeded the storage limit on your mailbox

    Description You may receive an error You have exceeded the storage limit on your mailbox Delete some items from your mai
  • 前端--三种插件用来解析mardowm,转化成为html语法

    前端 三种插件用来解析mardowm 转化成为html语法 使用方式十分简单 快捷 参考地址 1 markdown js 下载地址 https github com evilstreak markdown js div div
  • IBCS虚拟专线公网IP在公司内部搭建ERP系统按教程

    企业资源计划 ERP 系统是现代企业不可或缺的组成部分 可以将各个业务领域的信息整合到一个系统中 以实现信息共享 协调和协作 然而 随着企业规模的扩大 企业的ERP系统也需要相应地进行升级和扩展 因此 使用IBCS虚拟专线公网IP在公司内部
  • 五. Zuul 限流

    目录 一 spring cloud zuul ratelimit 基础解释 二 实现案例 1 pom 添加依赖 2 yml 配置 3 redis 配置类 4 自定义Zuul过滤器 5 自定义限流策略key 6 在当前Zuul服务中编写Con
  • string查找和替换

    string查找和替换 查找 查找指定字符串是否存在 替换 在指定的位置替换字符串 函数原型 int find const string str int pos 0 const 查找str第一次出现位置 从pos开始查找 int find
  • python读取串口数据 绘图_3.使用串口读取IMU数据并通过话题发布

    0x00 简介 我们的IMU扩展板是支持通过串口方式来读取IMU数据 现在代码已经开发完成 前面文章介绍的都是将IMU板插在树莓派上 然后使用树莓派的IIC接口来数据通信 因此不需要额外接线就可以发布imu话题的 若使用串口进行通信的话 若
  • 在Linux下安装jdk的步骤

    1 下载安装包 http www oracle com technetwork java javase downloads jdk8 downloads 2133151 html 版本 jdk 8u191 linux x64 tar gz

随机推荐

  • 确实卷,公司新来的00后卷王,我们这帮老油条真干不过.....

    都说00后躺平了 但是有一说一 该卷的还是卷 这不 前段时间我们公司来了个00后 工作没两年 跳槽到我们公司起薪18K 都快接近我了 后来才知道人家是个卷王 从早干到晚就差搬张床到工位睡觉了 最近和他聊了一次天 原来这位小老弟家里条件不太好
  • C#反编译工具:ILSpy

    参考 反编译软件ILSpy的使用教程 TONY5388的博客 CSDN博客 ilspy exe 总结 以前以为dnspy是反编译的 结果发现iLSpy是真的好用 可以选择生成不同C 版本的源码
  • SQLite数据库总结

    参考网址 https www cnblogs com stephen liu74 archive 2012 02 29 2328348 html 3种工作模式 1 SQLite完全内存数据库 在SQLite中 数据库通常是存储在磁盘文件中的
  • 【python】KNN模型训练及应用01

    目的应用 让电脑代替人工对图片分类 1 数据加载 from sklearn datasets import load iris from sklearn model selection import train test split fro
  • 今天终于知道了如果用layero获取layer弹窗中的子元素了

    通过layer弹出的ifram 想要获取里面的元素并且绑定相应的事件 以前一直不知道layero是什么意思 可以通过下面的代码自己体会一下 layer open type 2 title 文件管理 shadeClose true shade
  • 基于XStream的JavaBean与XML相互转换

    相对于JAXB XStream更简洁一些 常用注解 XStreamAlias 定义xml节点名 1 引入XStream依赖
  • 数据清洗分析导出遇到的一些问题

    本文简单记录一个学习过程 无技术含量 勿喷 环境 ambari 2 6 1 spark 2 1 python 3 6 oracle 11 2 sqoop 1 4 最近一直在测试数据采集 清洗 分析 导出 展示的一系列的工作 主要数据流程如下
  • 服务器定时重启问题排查

    上周主要处理了 两个生产问题 工作电脑没带 主要简述一下 每天的20 13分linux服务器 centos7 4 重新启动 应用服务接口类交易 耗时20秒 频发 这里先说一下服务器重启的问题 此次重启共发生三天 第一次主要排查管控平台 发现
  • 压缩感知与磁共振成像

    01 压缩感知原理和建模 传统的数据采样和重构需要遵循Nyquist采样定律 即采样频率必须大于信号频率带宽的2倍 才能完整的重建信号 如果采样频率低于2倍的频率带宽 信号在频域频谱搬移后就会发生混叠 产生伪影 压缩感知 Compresse
  • 【千奇百怪】PHP代码质检工具PHPCS分析介绍与使用

    前两天 还是在对一个代码质量检测平台维护的时候 遇到了好几个关于PHP质检的需求 而老平台上支持的php在新平台还未实现 于是简单研究了一下php的质检工具 准备接入新平台 系列文章目录 java自定义spotbugs检测器 PHP代码质检
  • cutlass 第一节:下载 编译 运行 cutlass 的一些备忘信息 ubuntu docker

    v100 cutlass start web site https developer nvidia com blog cutlass linear algebra cuda https github com NVIDIA cutlass
  • Qt开发 之 QWidget 和 QtQuick(QML) 写网页

    文章目录 1 准备工作 1 1 环境配置 1 2 Emsdk配置 1 2 1 配置环境文件 1 2 2 配置Emsdk的编译器 2 写两个简单的QWidget和QtQuick示例 2 1 QWidget 2 2 QtQuick 3 编译运行
  • 【KEIL-MDK】系列——主题配色

    文章目录 前言 一 更改主题配色 1 备份默认主题 2 替换配置文件 二 主题一 Sublime Theme风格 三 主题二 亮色风格 四 自定义主题配色 字体 下载地址 总结 前言 好看的主题 好看的界面 可以潜移默化的帮助我们提高生产力
  • 测试总结:如何写接口测试用例

    目录 一 接口测试用例基础知识 1 接口测试要测的是什么 2 接口测试的意义 二 接口测试用例设计方法 1 功能 检查接口基础功能 是否完成了业务逻辑要求 2 数据 分析接口的输入参数 覆盖各种可能的场景 3 性能 接口是否造成性能瓶颈 能
  • ctf-ping命令执行

    GXYCTF2019 Ping Ping Ping 现在做一下关于常见的绕过ping执行其他命令的姿势 启动环境 连接并输入参数 查看当前目录下都有什么 ls命令没有被过滤 并且知道flag就在这个目录下面 用cat查看的flag的时候发现
  • 降维和特征选择的关键方法介绍及MATLAB实现

    目录 概念理解 降维 特征选择 降维的方法 主成分分析 Principle Component Analysis PCA 方法 偏最小二乘法 Partial Least Squares PLS MATLAB实现 重点函数解读 例 光谱数据主
  • 数字货币DCEP

    上周新闻提到了区块链技术 号召大家学习和利用区块链技术 然后数字货币DCEP就浮出了水面 那么这个DCEP是什么呢 我根据自己的经验介绍下 如有不对请指正 DCEP是什么 DCEP是Digital Currency Electronic P
  • 软文营销创造优质内容才能打开市场产生共鸣

    内容是有效软文营销的基石 可满足多种用途 一般企业宣传都会以内容展现在网络上 形式可能包含新闻媒体 自媒体 论坛 问答 视频和其他形式 这些内容形式可以帮助生成 促进你的品牌知名度提升并增加业务收入 内容为王 只有内容优质才能在营销中产生共
  • Java实现区块链 --- 原理篇

    什么是区块链 区块链是由一个个记录着各种信息的小区块链接起来组成的一串链条 和链表类似 是一种数据结构 应用于未来互联化的社会 区块链特性 去中心化 区块链是分布式存储的 不存在中心点 所有每个节点都可以是中心 在生活中像银行 支付宝就属于
  • FFmpeg中编码类型为rawvideo无须解码直接显示测试代码

    在 https blog csdn net fengbingchun article details 93975325 中介绍过通过FFmpeg可以直接获取usb视频流并解码显示的测试代码 当时通过usb获取到的视频流编码类型为AV COD