您好,欢迎访问三七文档
本文内容主要来源于网络1.定义V4L2(VideoForLinuxTwo)是内核提供给应用程序访问音、视频驱动的统一接口。2.工作流程:打开设备-检查和设置设备属性-设置帧格式-设置一种输入输出方法(缓冲区管理)-循环获取数据-关闭设备。3.设备的打开和关闭:#includefcntl.hintopen(constchar*device_name,intflags);#includeunistd.hintclose(intfd);例:intfd=open(“/dev/video0”,O_RDWR);//打开设备close(fd);//关闭设备注意:V4L2的相关定义包含在头文件linux/videodev2.h中.4.查询设备属性:VIDIOC_QUERYCAP相关函数:intioctl(intfd,intrequest,structv4l2_capability*argp);相关结构体:structv4l2_capability{u8driver[16];//驱动名字u8card[32];//设备名字u8bus_info[32];//设备在系统中的位置u32version;//驱动版本号u32capabilities;//设备支持的操作u32reserved[4];//保留字段};capabilities常用值:V4L2_CAP_VIDEO_CAPTURE//是否支持图像获取例:显示设备信息structv4l2_capabilitycap;ioctl(fd,VIDIOC_QUERYCAP,&cap);printf(“DriverName:%s\nCardName:%s\nBusinfo:%s\nDriverVersion:%u.%u.%u\n”,cap.driver,cap.card,cap.bus_info,(cap.version16)&0XFF,(cap.version8)&0XFF,cap.version&0XFF);5.设置视频的制式和帧格式制式包括PAL,NTSC,帧的格式个包括宽度和高度等。相关函数:intioctl(intfd,intrequest,structv4l2_fmtdesc*argp);intioctl(intfd,intrequest,structv4l2_format*argp);相关结构体:v4l2_cropcap结构体用来设置摄像头的捕捉能力,在捕捉上视频时应先先设置v4l2_cropcap的type域,再通过VIDIO_CROPCAP操作命令获取设备捕捉能力的参数,保存于v4l2_cropcap结构体中,包括bounds(最大捕捉方框的左上角坐标和宽高),defrect(默认捕捉方框的左上角坐标和宽高)等。v4l2_format结构体用来设置摄像头的视频制式、帧格式等,在设置这个参数时应先填好v4l2_format的各个域,如type(传输流类型),fmt.pix.width(宽),fmt.pix.heigth(高),fmt.pix.field(采样区域,如隔行采样),fmt.pix.pixelformat(采样类型,如YUV4:2:2),然后通过VIDIO_S_FMT操作命令设置视频捕捉格式。如下图所示:5.1查询并显示所有支持的格式:VIDIOC_ENUM_FMT相关函数:intioctl(intfd,intrequest,structv4l2_fmtdesc*argp);相关结构体:structv4l2_fmtdesc{u32index;//要查询的格式序号,应用程序设置enumv4l2_buf_typetype;//帧类型,应用程序设置u32flags;//是否为压缩格式u8description[32];//格式名称u32pixelformat;//格式u32reserved[4];//保留};例:显示所有支持的格式structv4l2_fmtdescfmtdesc;fmtdesc.index=0;fmtdesc.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;printf(Supportformat:\n);while(ioctl(fd,VIDIOC_ENUM_FMT,&fmtdesc)!=-1){printf(\t%d.%s\n,fmtdesc.index+1,fmtdesc.description);fmtdesc.index++;}5.2查看或设置当前格式:VIDIOC_G_FMT,VIDIOC_S_FMT检查是否支持某种格式:VIDIOC_TRY_FMT相关函数:intioctl(intfd,intrequest,structv4l2_format*argp);相关结构体:structv4l2_format{enumv4l2_buf_typetype;//帧类型,应用程序设置unionfmt{structv4l2_pix_formatpix;//视频设备使用structv4l2_windowwin;structv4l2_vbi_formatvbi;structv4l2_sliced_vbi_formatsliced;u8raw_data[200];};};structv4l2_pix_format{u32width;//帧宽,单位像素u32height;//帧高,单位像素u32pixelformat;//帧格式enumv4l2_fieldfield;u32bytesperline;u32sizeimage;enumv4l2_colorspacecolorspace;u32priv;};例:显示当前帧的相关信息structv4l2_formatfmt;fmt.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;ioctl(fd,VIDIOC_G_FMT,&fmt);printf(“Currentdataformatinformation:\n\twidth:%d\n\theight:%d\n”,fmt.fmt.pix.width,fmt.fmt.pix.height);structv4l2_fmtdescfmtdesc;fmtdesc.index=0;fmtdesc.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;while(ioctl(fd,VIDIOC_ENUM_FMT,&fmtdesc)!=-1){if(fmtdesc.pixelformat&fmt.fmt.pix.pixelformat){printf(“\tformat:%s\n”,fmtdesc.description);break;}fmtdesc.index++;}例:检查是否支持某种帧格式structv4l2_formatfmt;fmt.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;fmt.fmt.pix.pixelformat=V4L2_PIX_FMT_RGB32;if(ioctl(fd,VIDIOC_TRY_FMT,&fmt)==-1)if(errno==EINVAL)printf(“notsupportformatRGB32!\n”);6.图像的缩放VIDIOC_CROPCAP相关函数:intioctl(intfd,intrequest,structv4l2_cropcap*argp);intioctl(intfd,intrequest,structv4l2_crop*argp);intioctl(intfd,intrequest,conststructv4l2_crop*argp);相关结构体:Cropping和scaling主要指的是图像的取景范围及图片的比例缩放的支持。Crop就是把得到的数据作一定的裁剪和伸缩,裁剪可以只取样我们可以得到的图像大小的一部分,剪裁的主要参数是位置、长度、宽度。而scale的设置是通过VIDIOC_G_FMT和VIDIOC_S_FMT来获得和设置当前的image的长度,宽度来实现的。看下图我们可以假设bounds是sensor最大能捕捉到的图像范围,而defrect是设备默认的最大取样范围,这个可以通过VIDIOC_CROPCAP的ioctl来获得设备的crap相关的属性v4l2_cropcap,其中的bounds就是这个bounds,其实就是上限。每个设备都有个默认的取样范围,就是defrect,就是defaultrect的意思,它比bounds要小一些。这个范围也是通过VIDIOC_CROPCAP的ioctl来获得的v4l2_cropcap结构中的defrect来表示的,我们可以通过VIDIOC_G_CROP和VIDIOC_S_CROP来获取和设置设备当前的crop设置。6.1设置设备捕捉能力的参数相关函数:intioctl(intfd,intrequest,structv4l2_cropcap*argp);相关结构体:structv4l2_cropcap{enumv4l2_buf_typetype;//数据流的类型,应用程序设置structv4l2_rectbounds;//这是camera的镜头能捕捉到的窗口大小的局限structv4l2_rectdefrect;//定义默认窗口大小,包括起点位置及长,宽的大小,大小以像素为单位structv4l2_fractpixelaspect;//定义了图片的宽高比};6.2设置窗口取景参数VIDIOC_G_CROP和VIDIOC_S_CROP相关函数:intioctl(intfd,intrequest,structv4l2_crop*argp);intioctl(intfd,intrequest,conststructv4l2_crop*argp);相关结构体:structv4l2_crop{enumv4l2_buf_typetype;//应用程序设置structv4l2_rectc;}7.videoInputsandOutputsVIDIOC_G_INPUT和VIDIOC_S_INPUT用来查询和选则当前的input,一个video设备节点可能对应多个视频源,比如saf7113可以最多支持四路cvbs输入,如果上层想在四个cvbs视频输入间切换,那么就要调用ioctl(fd,VIDIOC_S_INPUT,&input)来切换。VIDIOC_G_INPUTandVIDIOC_G_OUTPUT返回当前的videoinput和output的index.相关函数:intioctl(intfd,intrequest,structv4l2_input*argp);相关结构体:structv4l2_input{__u32index;/*Whichinput*/__u8name[32];/*Label*/__u32type;/*Typeofinput*/__u32audioset;/*Associatedaudios(bitfield)*/__u32tuner;/*Associatedtuner*/v4l2_std_idstd;__u32status;__u32reserved[4];};我们可以通过VIDIOC_ENUMINPUTandVIDIOC_ENUMOUTPUT分别列举一个input或者output的信息,我们使用一个v4l2_input结构体来存放查询结果,这个结构体中有一个index域用来指定你索要查询的是第几个input/ouput,如果你所查询的这个input是当前正在使用的,那么在v4l2_input还会包含一些当前的状态信息,如果所查询的input/output不存在,那么回返回EINVAL错误,所以,我们通过循环查找,直到返回错误来遍历所有的input/output.VIDIOC_G_INPUTandVIDIOC_G_OUTPUT返回当前的videoinput和output的index.例:列举当前输入视频所支持的视频格式structv4l2_inputinput;structv4l2
本文标题:V4L2超详细讲解
链接地址:https://www.777doc.com/doc-5277075 .html