Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2192187
  • 博文数量: 866
  • 博客积分: 14125
  • 博客等级: 上将
  • 技术积分: 10638
  • 用 户 组: 普通用户
  • 注册时间: 2007-07-27 16:53
个人简介

https://github.com/landuochong

文章分类

全部博文(866)

文章存档

2019年(3)

2018年(1)

2017年(10)

2015年(3)

2014年(8)

2013年(3)

2012年(70)

2011年(103)

2010年(360)

2009年(283)

2008年(22)

分类: C/C++

2010-12-27 10:16:13

v4l与Qt做图像采集。主要写了两文件,第一个v4l.h,第二个就应用程序testcv.cpp 本人水平有限,代码不完善地方希望被指正。
 
      v4l.h内容如下:
  1 #ifndef _V4L_H_
  2 #define _V4L_H_
  3 #endif
  4 #define DEFAULT_DEVICE "/dev/video0"     //v4l默认设备名称。
  5 #define VIDEO_MAXFRAME 2
  6 #define TRUE 1
  7 #define FALSE 0
  8 #include
  9 #include
 10 #include
 11 #include
 12 #include
 13 #include
 14 #include                          //v4l的头文件,里面有多种关键结构定义。
 15 #include
 16 #include
 17 struct _v4l_struct
 18
 19 {   int fd;                                             
 20     struct video_capability capability;
 21     struct video_picture picture;
 22     struct video_mmap mmap;
 23     struct video_mbuf mbuf;
 24     unsigned char *map;
 25     int frame_current;
 26     int frame_using[VIDEO_MAXFRAME];
 27 };
 28
 29 typedef struct _v4l_struct v4l_device;
 30
 31  int v4l_open (char *,v4l_device *);                    //打开视频设备
 32  int v4l_close (v4l_device *);                              //关闭视频设备
 33  int v4l_get_capability (v4l_device *);                //获取设备关于结构体video_capability的信息.
 34  int v4l_get_picture (v4l_device *);                    //获取设备关于结构体video_picture的信息
 35  int v4l_get_mbuf (v4l_device *);                       //向系统申请获得摄像头图像大小的内存空间
 36  int v4l_set_picture (v4l_device *,int,int,int,int,int);   //设置更改picture属性。
 37  int v4l_grab_picture (v4l_device *,unsigned int);    //直接使用read()读取设备,图像信息首地址map
 38  int v4l_mmap_init(v4l_device *);                            //向系统申请建立设备文件的共享内存空间
 39  int v4l_grab_init(v4l_device *,int,int);                     //获取图像信息前的初始化
 40  int v4l_grab_frame(v4l_device *,int);                     //获取图像信息函数
 41  int v4l_grab_sync(v4l_device *);                           //图像获取同步函数
 42  unsigned char * v4l_get_frame_adress(v4l_device *);    //图像信息地址返回函数
 43
 44
 45 int v4l_open (char * dev,v4l_device *vd)
 46 {if(!dev) {dev=DEFAULT_DEVICE;}
 47 if((vd->fd=open(dev,O_RDWR))<0) {perror("v4l_open:");return -1;}
 48 if(v4l_get_capability(vd)) return -1;
 49 if(v4l_get_picture(vd))return -1;
 50  return 0;
 51 }
 52
 53  int v4l_close (v4l_device *vd)
 54  {close(vd->fd);
 55   return 0; }
 56
 57 int v4l_get_capability(v4l_device *vd)
 58 {if (ioctl(vd->fd,VIDIOCGCAP,&(vd->capability))<0)
 59   {perror("v4l_get_capability:");return -1;}
 60     return 0;
 61 }
 62
 63  int v4l_get_picture(v4l_device *vd)
 64 {if (ioctl(vd->fd,VIDIOCGPICT,&(vd->picture))<0)
65    {perror("v4l_get_picture:");return -1;}
 66  return 0;
 67 }
 68
 69  int v4l_get_mbuf(v4l_device *vd)
 70  {if (ioctl(vd->fd,VIDIOCGMBUF,&(vd->mbuf))<0)
 71     {perror("v4l_get_mbuf:");return -1;}
 72 return 0;
 73 }
 74
 75 int v4l_set_picture(v4l_device *vd,int br,int hue,int col,int cont,int white    )
 76 {vd->picture.brightness=br;
 77  vd->picture.hue=hue;
 78  vd->picture.colour=col;
 79  vd->picture.contrast=cont;
 80  vd->picture.whiteness=white;
 81 if (ioctl(vd->fd,VIDIOCSPICT,&(vd->picture))<0)
 82     {perror("v4l_set_picture:");return -1;}
 83 return 0;
 84 }
 85
 86
 87 int v4l_grab_picture(v4l_device *vd,unsigned int size)
 88 {if (read(vd->fd,&(vd->map),size)==0)
 89  {perror("v4l_grab_picture:");return -1;}
 90  return 0;
 91 }
 92
 93 int v4l_mmap_init(v4l_device * vd)
 94 { if (v4l_get_mbuf(vd)<0) return -1;
 95  if ((vd->map=( unsigned char*)mmap(0,vd->mbuf.size,PROT_READ|PROT_WRITE,MAP    _SHARED,vd->fd,0))<0)
 96 {perror("v4l_mmap_init:mmap");return -1;}
 97 return 0;
 98  }
 99
100
101 int v4l_grab_init(v4l_device *vd, int width, int height)
102 {vd->mmap.width = width;
103  vd->mmap.height = height;
104  vd->mmap.format = vd->picture.palette;
105  vd->frame_current = 0;
106  vd->frame_using[0] = FALSE;
107  vd->frame_using[1] = FALSE;
108  return v4l_grab_frame(vd, 0);
109 }
110
111
112 int v4l_grab_frame(v4l_device *vd ,int frame)
113 { if (vd->frame_using[frame])
114   {fprintf(stderr,"v4l_grab_frame:frame %d is already used.\n",frame);    return -1;}
115   vd->mmap.frame=frame;
116   if (ioctl(vd->fd,VIDIOCMCAPTURE,&(vd->mmap))<0)
117     {perror("v4l_grab_frame");return -1;}
118 vd->frame_using[frame]=TRUE;
119 vd->frame_current=frame;
120 return 0;
121 }
122
123
124  int v4l_grab_sync(v4l_device * vd)
125 { if (ioctl(vd->fd,VIDIOCSYNC,&(vd->frame_current))<0)
126             {perror("v4l_grab_sync:");}
127 vd->frame_using[vd->frame_current]=FALSE;
128 return 0;
129 }
130
131
132  unsigned char * v4l_get_frame_adress(v4l_device * vd)
133  {return (vd->map+vd->mbuf.offsets[vd->frame_current]);
134      }
 


 testcv.cpp内容如下:
  1 extern "C"
  2 {
  3 #include "v4l.h"
     }
  5
  6 #define DEFAULT_PALETTE VIDEO_PALETTE_RGB24
  7 #include
  8 #include
  9 #include
 10 #include
 11 #include
 12 #include
 13 #include
 14 int main(int argc,char ** argv)
 15
 16 {          QApplication a(argc,argv);
 17            v4l_device vd;
 18            unsigned char * data;
 19            QImage image;
 20            QDateTime time=QDateTime::currentDateTime();
 21            QString filename=time.toString("yyyy.MMMM.dd hh:mm:ss");
 22            QString format=".jpg" ;
 23            filename.append(format);
 24            v4l_open(DEFAULT_DEVICE,&vd);
 25            v4l_mmap_init(&vd);
 26            v4l_grab_init(&vd,320,240);
 27            v4l_grab_sync(&vd);//此时就已经获得了一帧的图像,存在vd.map中
 28         data=v4l_get_frame_adress(&vd);
 29           if(!(image.loadFromData(data,vd.mbuf.size)))
 30           {perror("image is failly loaded\n");exit(1);}
 31           if(!(image.save(filename,"JPG")))
 32               {perror("image save fail\n");exit(1);}
 33           exit(0);
 34 return 0;
 35 }

编译后,插上摄像头后运行程序,在当前目录下生成以当前时间命名的jpg格式的图片。
阅读(1890) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~
评论热议
请登录后评论。

登录 注册