Linux上位机开发实战(camera视频读取)

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】

关于linux camera,一般都是认为是mipi camera,或者是usb camera。当然不管是哪一种,底层的逻辑都是v4l2,这一点大家都一样。只不过如果使用mipi camera,不仅要适配i2c驱动、mipi驱动、isp驱动,而且相关的协议手册、驱动代码,soc芯片厂家也未必提供的,这一点就比较麻烦。相比较而言,usb camera容易很多,sensor侧的i2c、mipi已经不用自己处理,isp也是usb camera内部的mcu处理好了,所以剩下来的工作,就是usb uvc协议处理。这是一个标准协议。用起来比较方便,也不需要安装额外的驱动,一般linux kernel都包含在内了。

在linux上面要获取图像有两种软件接口,一种就是借助于opencv来处理;另外一种就是自己编写对应的v4l2接口。

1、opencv接口

opencv是我们能够想到的,最简单、最直接的方法。不管是windows平台,还是linux平台,都可以通过opencv来获取图像。获取视频的流程基本就是三步。第一步,创建cv::VideoCapture对象。这个对象的输入参数可以是阿拉伯数字,也可以是具体的文件名。如果是后一种情况,那么就变成从视频读取数据了。

第二步,确认设备是否打开。这一步就是调用一下isOpened()函数即可。第三步,就是直接从cv::VideoCapture导出图像给cv::Mat,导出的方法使用的运算符>>,非常形象。

复制代码
#include <opencv2/opencv.hpp>
#include <iostream>

//#pragma comment(lib, "D:/software/opencv/build/x64/vc16/lib/opencv_world480d.lib")

int main() 
{
    cv::VideoCapture cap(0);

    if (!cap.isOpened()) 
    {
        return -1;
    }

    cv::Mat frame; 
    while (true) 
    {
        cap >> frame;
        if (frame.empty()) 
        {
            break;
        }

        cv::imshow("video", frame);
        if (cv::waitKey(30) == 27) 
        {
            break;
        }
    }

    cap.release();
    cv::destroyAllWindows();

    return 0;
}

2、v4l2接口

v4l2接口是另外一种用的比较多的方式。和opencv相比较,v4l2肯定处理流程上更加复杂一点,但是好处就是我们可以通过v4l2对摄像头做更加精准的控制。一种比较通用的情况就是,我们在实际使用的时候,都会关闭自动曝光,然后通过外部补充光源的形式,实现对光源的精确控制,从而可以保证可以稳定输出高质量的图片。

另外,对于一些自定义的v4l2接口,也是没有办法通过opencv来实现的。所以,对于很多稍微有点规模的图像处理公司来说,它们习惯于自己编写统一的图像接口,兼容windows的directshow和linux的v4l2,这样就不会受到两个平台的约束,类似于这样的api接口,

复制代码
#ifndef _CAMERA_API_H
#define _CAMERA_API_H

#ifdef EXPORTS
#define DLLAPI __declspec(dllexport)
#else
#define DLLAPI __declspec(dllimport)
#endif

extern "C" 
{
DLLAPI int  CameraNumber();
DLLAPI int  EnumCameraIndex(char* vid, char* pid, unsigned char CamIndex[32]);
DLLAPI void*  CameraOpen(int index, int nWidth = 0, int nHeight = 0, const char* data_type = "");
DLLAPI int  CameraClose(void* pCamDev);
DLLAPI int  CameraWidth(void* pCamDev);
DLLAPI int  CameraHeight(void* pCamDev);
DLLAPI char* CameraDataType(void* pCamDev);
DLLAPI char* CameraName(void* pCamDev);
DLLAPI int  CameraQuery(void* pCamDev, unsigned char* szImageBuf);
}

#endif
相关推荐
晨曦夜月7 分钟前
头文件与目标文件的关系
linux·开发语言·c++
Xyz996_7 分钟前
Ansible进行Nginx编译安装的详细步骤
运维·ansible
白仑色8 分钟前
java中的anyMatch和allMatch方法
java·linux·windows·anymatch·allmatch
云和数据.ChenGuang12 分钟前
自动化运维工程师之ansible启动rpcbind和nfs服务
运维·服务器·运维技术·数据库运维工程师·运维教程
yimengsama13 分钟前
VMWare虚拟机如何连接U盘
linux·运维·服务器·网络·windows·经验分享·远程工作
松涛和鸣17 分钟前
32、Linux线程编程
linux·运维·服务器·c语言·开发语言·windows
云和数据.ChenGuang19 分钟前
AB压力测试运维工程师技术教程
运维·压力测试·运维工程师
꧁坚持很酷꧂20 分钟前
把虚拟机Ubuntu中的USB设备名称改为固定名称
linux·数据库·ubuntu
少年白char32 分钟前
【AI漫剧】开源自动化AI漫剧生成工具 - 从文字到影像:AI故事视频创作的全新可能
运维·人工智能·自动化
容智信息35 分钟前
容智Report Agent智能体驱动财务自动化,从核算迈向价值创造
大数据·运维·人工智能·自然语言处理·自动化·政务