Qt(c++)调用海康威视监控摄像头

文章目录

  • 一.海康威视监控摄像头开发SDK介绍
  • 二.海康SDK模块说明
  • 三.Qt项目中海康威视SDK配置
  • 四.实时预览摄像头图像程序

一.海康威视监控摄像头开发SDK介绍

设备网络SDK是基于设备私有网络通信协议开发的,为嵌入式网络硬盘录像机、NVR、网络摄像机、网络球机、视频服务器、解码器、报警主机、网络存储等产品服务的配套模块,用于远程访问和控制设备软件的二次开发。图像预览, 文件回放和下载, 云台控制, 布防/撤防, 语音对讲, 日志管理, 解码卡, 远程升级, 远程重启/关闭, 格式化硬盘, 参数配置(系统配置, 通道配置, 串口配置, 报警配置, 用户配置), 多路解码器, 智能设备功能和获取设备能力集等。
海康威视SDK下载地址:https://open.hikvision.com/download/5cda567cf47ae80dd41a54b3?type=10

在这里插入图片描述

二.海康SDK模块说明

Windows下设备网络SDK:

在这里插入图片描述

Linux下设备网络SDK库:
在这里插入图片描述
设备网络SDK开发包中包含以上各个组件,HCNetSDK.dllHCCore.dll必须加载,其他组件,用户可以根据需要选择其中的一部分或者全部,以下将对各个组件在SDK中的作用和使用条件分别说明。

  • 网络通讯库:设备网络SDK的主体,主要用于网络客户端与各类产品之间的通讯交互,负责远程功能调控, 远程参数配置及码流数据的获取和处理等。设备网络 SDK V5.0针对产品应用业务进行细化,对之前版本的SDK的功能模块进行组件化,其中外部接口(HCNetSDK.dll)仍然保持和设备网络SDK V4.x版本保存一致(向下兼容),其他单独的业务功能(预览、回放等)可以加载单独的模块组件,多个业务功能也可以组合使用。更新SDK时,HCNetSDK.dllHCCore.dll以及HCNetSDKCom文件夹下的功能组件库文件都需要更新加载,且HCNetSDKCom文件夹名不能修改。

  • hpr库:网络通讯库的依赖库,Linux SDK使用时和网络通讯库同时加载。

  • RTSP通讯库:支持RTSP传输协议的网络库,当需要对支持RTSP协议的产品进行取流等操作时就必须加载该项组件。

  • 转封装库:库的功能可以分为两种:一种是将标准码流转换成采用本公司封装格式的码流。当用户需要对支持RTSP协议的产品捕获采用本公司封装格式的码流数据时(即当设置NET_DVR_RealPlay_V40接口中的回调函数捕获数据或者调用NET_DVR_SetRealDataCallBack接口捕获数据时)必须加载该组件。另一种功能是能将标准码流转换成其他格式的封装,如3GPP, PS等。例如,当用户需要对支持RTSP协议的产品实时捕获指定封装格式的码流数据(对应的SDK接口为NET_DVR_SaveRealData)时必须加载该项组件。

  • 字符转换库:电脑字符集和设备字符集不一致时,SDK内部需要进行字符编码转换,SDK默认使用libiconv库进行类型转换。如果用户不想使用libiconv编码库,可以调用NET_DVR_SetSDKLocalCfg(类型: NET_SDK_LOCAL_CFG_TYPE_BYTE_ENCODE)设置字符转码回调函数,将用户自己的字符编码接口告知SDK,然后SDK将使用用户提供的字符编码接口进行字符串处理。

  • 模拟能力集:如果需要获取设备能力集(NET_DVR_GetDeviceAbility),可以调用NET_DVR_SetSDKLocalCfg启用模拟能力集,此时需要加载LocalXml.zip(要求和网络通讯库放在同一个目录下)。

  • 语音对讲库:用于语音对讲时通过声卡采集数据并按照指定的编码格式编码码流或者解码播放音频码流数据(不带封装格式的码流数据)。V4.2.2.5及以前版本SDK均采用windows API实现相关功能。之后版本默认使用语音对讲库的方式,通过接口NET_DVR_SetSDKLocalCfg可以选择之前的windows API模式。OpenAL32.dll为依赖库,语音对讲库模式下必须加载。音频编解码目前仅Win32版本SDK支持。Linux系统下无语音对讲、语音广播、音频编解码功能,仅支持语音转发接口。

  • 帧分析库:用于分析视音频帧数据,调用NET_DVR_SetESRealPlayCallBackNET_DVR_SetPlayBackESCallBack设置裸码流回调函数等接口时,必须加载该库文件。

  • OpenSSL库:用于登录以及敏感信息加密,必须加载该库文件。

  • 播放库:主要用于对实时码流数据进行解码显示(实现预览功能)和对录像文件进行回放解码等。用户如果需要在SDK内部进行对实时流和录像码流播放显示时(即NET_DVR_RealPlay_V40接口的第二个结构体参数的播放句柄设置成有效句柄时)必须加载该组件,而如果用户仅需要用网络通讯库捕获到数据后再外部自行处理就不需要加载该组件,这种情况下用户在外部自行解码将更灵活,可参见播放库SDK开发包里面的《播放器SDK编程指南》。

三.Qt项目中海康威视SDK配置

  1. 解压下载好的SDK压缩包,复制SDK解压包中的文件(库文件->include)(头文件->lib)到自己新建的文件夹中
    在这里插入图片描述

  2. 系统环境变量添加lib文件夹路径在这里插入图片描述

  3. Qt项目中CMakeList.txt添加如下代码,这样即可完成海康威视的SDK导入

    # HKVISION
    set(HKVISION_DIR "C:\\Program Files\\HKVISION")
    set(HKVISION_INCLUDE_DIR "C:\\Program Files\\HKVISION\\include")
    set(HKVISION_LIB_DIRS "C:\\Program Files\\HKVISION\\lib")
    include_directories(${HKVISION_INCLUDE_DIR})
    link_directories(${HKVISION_LIB_DIRS})
    
    target_link_libraries(${PROJECT_NAME} PUBLIC HCNetSDK PlayCtrl)
    

四.实时预览摄像头图像程序

海康官方的实时预览程序流程:
在这里插入图片描述

  1. 首先,先初始化海康的SDK

    // 1.初始化海康监控SDK
    NET_DVR_Init(); 
    
  2. 然后,创建一个包含摄像头IP等信息的NET_DVR_USER_LOGIN_INFO结构体和NET_DVR_DEVICEINFO_V40相机信息结构体,其中NET_DVR_USER_LOGIN_INFO结构体包含登录相机时需要提供的必要信息,例如用户名和密码,而NET_DVR_DEVICEINFO_V40结构体则是登录成功后,返回的相机的基本信息。

    // 2.设置连接相机的信息,用户注册设备
    NET_DVR_USER_LOGIN_INFO struLoginInfo = {0}; //包含相机参数的结构体
    NET_DVR_DEVICEINFO_V40 struDeviceInfoV40 = {0}; //登录后的相机信息
    
    struLoginInfo.bUseAsynLogin = 0; //同步登录方式
    strcpy_s(struLoginInfo.sDeviceAddress, "192.168.1.71"); //设备IP地址
    struLoginInfo.wPort = 8000; //设备服务端口
    strcpy_s(struLoginInfo.sUserName, "admin"); //设备登录用户名
    strcpy_s(struLoginInfo.sPassword, "1234"); //设备登录密码
    
    NET_DVR_Login_V40(&struLoginInfo, &struDeviceInfoV40); //设备登录
    

    NET_DVR_Login_V40()函数说明:
    在这里插入图片描述NET_DVR_USER_LOGIN_INFO结构体说明:在这里插入图片描述

  3. 相机登录成功后,我们就可以开启相机的实时预览,实时预览的方式有两种,一种是直接给个窗口ID(HWND),SDK会自动把图像显示到控件上,还有一种是给个回调函数,SDK会把图像数据返回到回调函数里,用户自行决定如何处理图像数据。这里只说明第一种方法,回调函数的方式可以自行去海康威视SDK说明文档中查看使用方式。无论采用何种方式,都需要提供NET_DVR_PREVIEWINFO结构体,这个结构体中包含了SDK如何对流进行处理的信息。

    //通过给控件的HWDN,SDK自行进行图像的显示
    // 3.启动预览
    LONG lUserID = -1; //注册设备ID
    LONG lRealPlayHandle = -1; //实时预览控制端口
    
    NET_DVR_PREVIEWINFO struPlayInfo; //实时显示参数设定
    struPlayInfo.hPlayWnd = hPlayWnd; //需要SDK解码时句柄设为有效值,仅取流不解码时可设为空, Qt中可以通过(HWND)ui->srcImg->winId()获取控件HWND
    struPlayInfo.lChannel = 1; //预览通道号
    struPlayInfo.dwStreamType = 0; //0-主码流,1-子码流,2-码流3,3-码流4,以此类推
    struPlayInfo.dwLinkMode = 0; //0- TCP方式,1- UDP方式,2- 多播方式,3- RTP方式,4-RTP/RTSP,5-RSTP/HTTP
    struPlayInfo.bBlocked = 0; //0- 非阻塞取流,1- 阻塞取流
    
    NET_DVR_RealPlay_V40(lUserID, &struPlayInfo, NULL, NULL);
    

NET_DVR_RealPlay_V40函数说明:
在这里插入图片描述

NET_DVR_PREVIEWINFO结构体说明:
在这里插入图片描述

4.一旦NET_DVR_RealPlay_V40()设置好后,SDK就会自动把图像流显示到绑定的控件中,如果需要从流中获取一帧的图像,可以通过NET_DVR_CapturePictureBlock_New()函数获取。

std::vector<char> inputData(3840*2160*4 + 54); //创建一个数组,大小为图像的H*W*4 + 54,用来保存图像数据
DWORD size= 0; //返回的实际图像大小
DWORD* psize = &size;  //指向实际图像大小的指针
NET_DVR_CapturePictureBlock_New(lRealPlayHandle, inputData.data(), (DWORD)inputData.size(), psize) //通过这个函数获取一帧图像数据

cv::_InputArray pic_arr(inputData); //将图像数据转换为OpenCV的数组
Mat grabImg = cv::imdecode(pic_arr, cv::IMREAD_COLOR); //OpenCV数组转换为Mat对象

//通过以下代码,把opencv的Mat转换为QImage,然后在Qt的QLabel控件上进行显示
QImage qgrabImg = QImage((const unsigned char*)(grabImg.data), grabImg.cols, grabImg.rows, grabImg.cols*grabImg.channels(), QImage::Format_RGB888);   // Mat为BGR颜色模式;
qgrabImg = qgrabImg.rgbSwapped();
ui->grabImg->setPixmap(QPixmap::fromImage(qgrabImg));

在这里插入图片描述

  1. 实际的Qt程序运行效果
    在这里插入图片描述

  2. 程序源代码下载地址
    地址: https://download.csdn.net/download/qq_30150579/87578614

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/576.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【Linux】冯诺依曼体系结构

冯诺依曼体系结构一、计算机结构体系来源二、冯诺依曼体系结构三、冯诺依曼体系结构中的数据流动一、计算机结构体系来源 研制电子计算机的想法产生于第二次世界大战期间&#xff0c;主要用来进行弹道计算&#xff0c;在"时间就是胜利"的战争年代&#xff0c;迫切需…

【JavaEE进阶篇1】认识Spring、认识IoC、使用spring创建对象

目录 一、什么是Spring 1.1容器 1.2什么是IoC 传统方式创建对象的问题&#xff1a; 类与类之间的耦合性过大 Ioc的优点 Spring IoC容器最核心的功能 1.3DI概念说明(Dependency Injection) IoC和DI的区别是什么 二、Spring项目的创建 三、Spring的使用(把对象存储到spr…

ChatGPT是如何训练得到的?通俗讲解

首先声明喔&#xff0c;我是没有任何人工智能基础的小白&#xff0c;不会涉及算法和底层原理。 我依照我自己的简易理解&#xff0c;总结出了ChatGPT是怎么训练得到的&#xff0c;非计算机专业的同学也应该能看懂。看完后训练自己的min-ChatGPT应该没问题 希望大牛如果看到这…

stm32外设-中断详解

0. 写在最前 本栏目笔记都是基于stm32F10x 1. 中断是啥&#xff1f; 什么是中断&#xff1a;CPU在处理某一事件A时&#xff0c;发生的另外某一事件B请求CPU去处理&#xff08;产生了中断&#xff09;&#xff0c;随后CPU暂时中断当前正在执行的任务&#xff0c;去对事件B进行处…

Java的二叉树、红黑树、B+树

数组和链表是常用的数据结构&#xff0c;数组虽然查找快&#xff08;有序数组可以通过二分法查找&#xff09;&#xff0c;但是插入和删除是比较慢的&#xff1b;而链表&#xff0c;插入和删除很快&#xff08;只需要改变一些引用值&#xff09;&#xff0c;但是查找就很慢&…

【C#】组件化开发,调用dll组件方法

系列文章 C#项目–业务单据号生成器&#xff08;定义规则、自动编号、流水号&#xff09; 本文链接&#xff1a;https://blog.csdn.net/youcheng_ge/article/details/129129787 C#项目–开始日期结束日期范围计算&#xff08;上周、本周、明年、前年等&#xff09; 本文链接&…

快排函数 -- qsort函数(Quick Sort)

文章目录&#x1f50e;1.qsort函数简介&#x1f4a1;1.1.函数原型&#x1f4a1;1.2.参数含义&#x1f50e;2.比较函数介绍&#x1f50e;3.比较函数使用案例&#x1f4a1;3.1.整型数组&#x1f4a1;3.2.浮点型数组&#x1f4a1;3.3.结构体类型 - 字符串&#x1f50e;4.利用冒泡排…

震撼,支持多模态模型的ChatGPT 4.0发布了

最近几个月&#xff0c;互联网和科技圈几乎ChatGPT刷屏了&#xff0c;各种关于ChatGPT的概念和应用的帖子也是围绕在周围。当去年年底ChatGPT发布的那几天&#xff0c;ChatGPT确实震撼到了所有人&#xff0c;原来AI还可以这么玩&#xff0c;并且对国内的那些所谓的人工智能公司…

Tesla都使用什么编程语言?

作者 | 初光 出品 | 车端 备注 | 转载请阅读文中版权声明 知圈 | 进“汽车电子与AutoSAR开发”群&#xff0c;请加微“cloud2sunshine” 总目录链接>> AutoSAR入门和实战系列总目录 带着对更美好未来的愿景&#xff0c;特斯拉不仅成为有史以来最有价值的汽车公司&…

多线程(初阶)

文章目录一.初始线程(Thread)1.1.线程的概念1.2.线程的优势1.2.1.线程比进程更轻量1.2.2.并发编程1.3.线程和进程的区别二.Thread类方法2.1. java 中创建线程的方法2.1.1. 继承Thread,重写run2.1.2. 实现Ruuable接口2.1.3. 使用匿名内部类,继承Thread2.1.4.使用匿名内部类,实现…

[蓝桥杯单片机]——八到十一届初赛决赛客观题

第八届初赛 一、填空题 采用外部12MHz晶振&#xff0c;经过系统12分频时定时器获得最大定时长度&#xff0c;此时定时器定时脉冲为1MHz&#xff0c;周期为1s&#xff0c;而定时器计时均为16位加法计数器&#xff0c;即计时长度为。 二、 选择题 ①带阻滤波器是指能通过大多数频…

处理窄区路径规划的业务问题

系列文章目录 提示&#xff1a;这里可以添加系列文章的所有文章的目录&#xff0c;目录需要自己手动添加 TODO:写完再整理 文章目录系列文章目录前言一、通过栅格地图的处理解决二、使用bug绕障的方式走出窄区&#xff0c;或者结合边界图形参考bug算法沿边出来三、使用维诺图计…

字符串函数和内存函数

&#x1f355;博客主页&#xff1a;️自信不孤单 &#x1f36c;文章专栏&#xff1a;C语言 &#x1f35a;代码仓库&#xff1a;破浪晓梦 &#x1f36d;欢迎关注&#xff1a;欢迎大家点赞收藏关注 字符串函数和内存函数 文章目录字符串函数和内存函数前言1. 字符串函数介绍1.1 s…

【MySQL】MySQL的优化(一)

目录 查看SQL执行频率 定位低效率执行SQL 定位低效率执行SQL-慢查询日志 定位低效率执行SQL-show processlist 查看SQL执行频率 MySQL 客户端连接成功后&#xff0c;通过 show [session|global] status 命令可以查看服务器状态信息。通 过查看状态信息可以查看对当…

jvm类与类加载

1.类加载过程&#xff1a; 首先要加载某个类一定是出于某种目的&#xff0c;比如要运行java程序&#xff0c;那么久必须加载主类才能运行其中的方法&#xff0c;所以一般在这些情况下&#xff0c;如果类没有被加载&#xff0c;就会自动被加载&#xff1a; 1.使用new创建对象时 …

MyBatis开发环境搭建

1.创建工程 2.引入相关的依赖 pom.xml <dependencies><!--1.引入mybatis包--><dependency><groupId>org.mybatis</groupId><artifactId>mybatis</artifactId><version>3.4.6</version></dependency><!--2.单元…

FPGA和IC设计怎么选?哪个发展更好?

很多人纠结FPGA和IC设计怎么选&#xff0c;其实往小了说&#xff0c;要看你选择的具体是哪个方向岗位。往大了说&#xff0c;将来你要是走更远&#xff0c;要成为大佬&#xff0c;那基本各个方向的都要有涉及的。 不同方向就有不同的发展&#xff0c;目前在薪资上IC设计要比FP…

Qt之高仿QQ系统设置界面

QQ或360安全卫士的设置界面都是非常有特点的,所有的配置项都在一个垂直的ScrollArea中,但是又能通过左侧的导航栏点击定位。这样做的好处是既方便查看指定配置项,又方便查看所有配置项。 一.效果 下面左边是当前最新版QQ的系统设置界面,右边是我的高仿版本,几乎一毛一样…

【Linux】进程的程序替换

文章目录1. 程序替换1.创建子进程的目的是什么&#xff1f;2.了解程序是如何进行替换的3. 程序替换的基本原理当创建进程的时候&#xff0c;先有进程数据结构&#xff0c;还是先加载代码和数据&#xff1f;程序替换是整体替换&#xff0c;不是局部替换execl 返回值4. 替换函数1…

【三维几何学习】从零开始网格上的深度学习-2:卷积网络CNN篇(Pytorch)

本文参加新星计划人工智能(Pytorch)赛道&#xff1a;https://bbs.csdn.net/topics/613989052 从零开始网格上的深度学习-2:卷积网络CNN篇引言一、概述1.1 卷积操作简述1.2 网格上的面卷积二、核心代码2.1 面卷积2.2 网络框架三、基于CNN的网格分类3.1 分类结果3.2 全部代码引言…
最新文章