Welcome 微信登录
编程资源 图片资源库 蚂蚁家优选 PDF转换器

首页 / 操作系统 / Linux / OK6410预览并实现截图操作(RGB565)

涉及内容:1、v4l2操作摄像头2、RGB565转BMP(RGB16)文件参考代码:#include <sys/time.h>
#include <sys/types.h>
#include <asm/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <sys/mman.h>
#include <errno.h>#include <jpeglib.h>#include <linux/fs.h>
#include <linux/kernel.h>
#include "videodev2.h"
#include <linux/fb.h> #include "jpeglib.h"#define CTRL_NUM 100#define WIDTH             480
#define HEIGHT              272
//文件头
struct tagBITMAPFILEHEADER{    unsigned long bfSize;
    unsigned long bfLeft;
    unsigned long bfOffBits;};
// bmp图像的位图信息头
struct tagBITMAPINFOHEADER{
    unsigned long biSize;
    unsigned long bmpWidth;
    unsigned long bmpHeight;
    unsigned short biPlanes;
    unsigned short bicolors;
    unsigned long isCompressed;
    unsigned long biMapSize;
    unsigned long biHorizontal;
    unsigned long biVertical;
    unsigned long biusedcolors;
    unsigned long biimportcolors;
};
#define V4L2_DEV_NODE "/dev/video1"
#define FB_DEV_NODE "/dev/fb0"
typedef struct v4l2_input    V_INPUT;
typedef struct v4l2_format V_FORMAT;
typedef struct v4l2_fmtdesc  V_FMTDESC;
typedef struct v4l2_queryctrl V_QRYCTRL;typedef struct fb_var_screeninfo F_VINFO; #define V4L2_FMT_IN  0
#define V4L2_FMT_OUT  1
unsigned char *preview_buf;
static void writebmp(int data_fd){
 int i,j,k,size;
 int ret; unsigned char *buf1 = (unsigned char *)malloc(sizeof(unsigned char) * 480*272*2);
 memcpy(buf1, preview_buf, 480*272*2); unsigned short buf[WIDTH*HEIGHT]={0};
 printf("Write buf[i*WIDTH+k] begin! ");
 for(i=0;i<HEIGHT;i++)
 {
    for(j=0;j<WIDTH;j++)
    {
   *(buf+i*WIDTH+j)= (buf1[i*WIDTH*2+j*2])|(buf1[i*WIDTH*2+j*2+1]<<8);
   //if(i<1)
   // printf("(%d,%d,0x%4x) ",i,j,*(buf+i*WIDTH+j));
  }
 }
 printf("Write buf[i*WIDTH+k] end! ");
 unsigned short bmp[WIDTH*HEIGHT];
   
 struct tagBITMAPFILEHEADER bfhead;
 struct tagBITMAPINFOHEADER binfohead;
 size=HEIGHT*WIDTH;
 
 
 bfhead.bfSize=0x36+size*2;
 bfhead.bfLeft=0;
 bfhead.bfOffBits=0x36;
 
 binfohead.biSize=0x28;
 binfohead.bmpWidth=WIDTH;
 binfohead.bmpHeight=HEIGHT;
 binfohead.biPlanes=1;
 binfohead.bicolors=0x10;
 binfohead.isCompressed=0;
 binfohead.biMapSize=size*2;
 binfohead.biHorizontal=0x0b13;
 binfohead.biVertical=0x0b13;
 binfohead.biusedcolors=0;
 binfohead.biimportcolors=0;
 
 for(i=0;i<HEIGHT;i++)
  for(j=0;j<WIDTH;j++)
    *(bmp+i*WIDTH+j)=((buf[(HEIGHT-i)*WIDTH-WIDTH+j]&0xf800)>>1)|((buf[(HEIGHT-i)*WIDTH-WIDTH+j]&0x07c0)>>1)|((buf[(HEIGHT-i)*WIDTH-WIDTH+j]&0x1f));
 //翻转图像  
 //for (i=HEIGHT; i>=0;i--)
 // for(j=WIDTH;j>=0;j--)
 //  *(bmp+i*WIDTH+j)=((buf[i*WIDTH+j]&0xf800)>>1)|((buf[i*WIDTH+j]&0x07c0)>>1)|((buf[i*WIDTH+j]&0x1f));
   
 write(data_fd,"BM",2);
 i=write(data_fd,&bfhead,sizeof(struct tagBITMAPFILEHEADER));
 printf("Write filehead %dbytes ",i);
 
 i=write(data_fd,&binfohead,sizeof(struct tagBITMAPINFOHEADER));
 printf("Write infohead %dbytes ",i);
 i=write(data_fd,bmp,size*2);
 printf("Write bitmap %dbytes ",i);
 
 lseek(data_fd,SEEK_SET,4);
}
int main(void)
{
 int v4l2_fd = -1;
 int fb_fd = -1;
 int n=0;
 __u8 *fb_buf;
 __u32 screensize;
 V_FORMAT fmt;
 struct v4l2_capability caminfo;
 
 v4l2_fd = open(V4L2_DEV_NODE, O_RDWR);
 if (v4l2_fd < 0) {
  printf(" open video ERR ");
 } fb_fd = open(FB_DEV_NODE, O_RDWR);
 if (fb_fd < 0) {
  printf(" open FB ERR ");
 }
 
 screensize = 480 * 272 * 16 / 8;
 fb_buf = (__u8 *)mmap(0, screensize, PROT_READ | PROT_WRITE, MAP_SHARED,
    fb_fd, 0);
 if ((int)fb_buf == -1) {
  printf("Error: failed to map framebuffer device to memory. ");
  close(fb_fd);
  return -1;
 } if((n =(ioctl(v4l2_fd, VIDIOC_QUERYCAP, &caminfo)))<0)
   printf("Error: failed to get camera info.%d ",n);
  //设置图象模式
  fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; fmt.fmt.pix.width = 480;
 fmt.fmt.pix.height = 272; fmt.fmt.pix.pixelformat = V4L2_PIX_FMT_RGB565;
 fmt.fmt.pix.priv = V4L2_FMT_OUT; 
 if((ioctl(v4l2_fd, VIDIOC_S_FMT, &fmt))<0)
  printf("Error: failed to set video format. "); int type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
 if((ioctl(v4l2_fd, VIDIOC_STREAMON, &type))<0)
  printf("start to get pic %d ",(int)fmt.fmt.pix.sizeimage); int ii = 0;
 while(1){
  n=read(v4l2_fd, fb_buf, 480*272*2);
  if (ii == 0 && n > 0) {
   int data_fd=-1;
   
   printf("read Data Length:%d ", n);
   preview_buf =  malloc(n);
   memcpy(preview_buf, fb_buf, n);
   
   
   char bmpfilename[30];
   sprintf(bmpfilename, "/sdcard/photo%d.bmp",1);
   
   if((data_fd = open(bmpfilename,O_CREAT|O_RDWR,0777))<0){
    printf("Error: failed to creat photo.bmp. ");
    return 0;
   }
   printf("bmpfilename is %s ",bmpfilename);   writebmp(data_fd);
   if(data_fd>0)
                  close(data_fd);
   free(preview_buf);
   ii = 1;
   }
 }}