char *fb_init_display(int fp, int width, int height, int left_x, int top_y, int bpp) { struct fb_var_screeninfo var; struct s5ptvfb_user_window window; int fb_size; char *fb = NULL; var.xres = width; var.yres = height; var.bits_per_pixel = bpp; window.x = left_x; window.y = top_y; var.xres_virtual = var.xres; var.yres_virtual = var.yres; var.xoffset = 0; var.yoffset = 0; var.width = 0; var.height = 0; var.transp.length = 0; var.activate = FB_ACTIVATE_FORCE; fb_size = var.xres_virtual * var.yres_virtual * bpp / 8; /* FBIOPUT_VSCREENINFO should be first */ put_vscreeninfo(fp, &var); fb_ioctl(fp, S5PTVFB_WIN_POSITION, &window); /* draw image */ fb = fb_mmap(fb_size, fp); memset(fb, 0x0, fb_size); return fb; }
/************ function implementation ********************/ int main(int argc, char *argv[]) { /* * declaration for jpeg decompression */ struct jpeg_decompress_struct cinfo; struct jpeg_error_mgr jerr; FILE *infile; unsigned char *buffer; /* * declaration for framebuffer device */ int fbdev; char *fb_device; unsigned char *fbmem; unsigned int screensize; unsigned int fb_width; unsigned int fb_height; unsigned int fb_depth; unsigned int x; unsigned int y; /* * check auguments */ /*if (argc != 2) { usage("insuffient auguments"); exit(-1); }*/ /* * open framebuffer device */ if((fb_device = getenv("FRAMEBUFFER")) == NULL) { fb_device = FB_DEV; } fbdev = fb_open(fb_device); /* * get status of framebuffer device */ fb_stat(fbdev, &fb_width, &fb_height, &fb_depth); printf("%d ", fb_width); printf("%d ", fb_height); printf("%d\n", fb_depth); /* * map framebuffer device to shared memory */ screensize = fb_width * fb_height * fb_depth / 8; fbmem = fb_mmap(fbdev, screensize); if(fbmem == 0) { printf("fb mmap error"); } /*open input jpeg file */ char jpgname[32] = {0}; int jpgcnt = 0; // SystemSetBlankInterVal(0); while(1) { //for(jpgcnt = 0; jpgcnt < 10; jpgcnt++) { /* * init jpeg decompress object error handler */ sprintf(jpgname, "%s","./picture.jpg"); //sprintf(jpgname, "/var/run/%d.jpg", jpgcnt); printf("begint to display %s\n", jpgname); cinfo.err = jpeg_std_error(&jerr); jpeg_create_decompress(&cinfo); if((infile = fopen(jpgname, "rb+")) == NULL) { fprintf(stderr, "open %s failed\n", "1.jpg"); exit(-1); } /* * bind jpeg decompress object to infile */ jpeg_stdio_src(&cinfo, infile); /* * read jpeg header */ jpeg_read_header(&cinfo, TRUE); /* * decompress process. * note: after jpeg_start_decompress() is called * the dimension infomation will be known, * so allocate memory buffer for scanline immediately */ jpeg_start_decompress(&cinfo); /*if ((cinfo.output_width > fb_width) || (cinfo.output_height > fb_height)) { printf("too large JPEG file,cannot display\n"); return (-1); }*/ buffer = (unsigned char *) malloc(cinfo.output_width * cinfo.output_components); y = 0; while(cinfo.output_scanline < cinfo.output_height) { jpeg_read_scanlines(&cinfo, &buffer, 1); if(fb_depth == 16) { unsigned short color; for(x = 0; x < cinfo.output_width; x++) { color = RGB888toRGB565(buffer[x * 3], buffer[x * 3 + 1] , buffer[x * 3 + 2]); fb_pixel(fbmem, fb_width, fb_height, x, y, color); } } else if(fb_depth == 24) { memcpy((unsigned char *) fbmem + y * fb_width * 3, buffer, cinfo.output_width * cinfo.output_components); } y++; // next scanline } /* * finish decompress, destroy decompress object */ jpeg_finish_decompress(&cinfo); jpeg_destroy_decompress(&cinfo); /* * release memory buffer */ free(buffer); /* * close jpeg inputing file */ fclose(infile); usleep(400000); } } /* * unmap framebuffer's shared memory */ fb_munmap(fbmem, screensize); /* * close framebuffer device */ fb_close(fbdev); return (0); }
int main(int argc,char **argv) { int ret; int numBufs = 0; unsigned char *buffer; /* * declaration for framebuffer device */ int fbdev; char *fb_device; unsigned char *fbmem; unsigned int screensize; unsigned int fb_width; unsigned int fb_height; unsigned int fb_depth; unsigned int x; unsigned int y; int fd; int nResult; struct InputData event; cam_fd = open("/dev/video0" ,O_RDWR); if(cam_fd < 0){ printf("can not open driver!! \n"); exit(1); } fd = open("/dev/input/event0", O_RDONLY|O_NONBLOCK); if(fd==-1) { perror("open(event0)"); return 1; } //设置帧格式 memset(&fmt,0,sizeof(fmt)); fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; // 数据流类型,必须永远是V4L2_BUF_TYPE_VIDEO_CAPTURE fmt.fmt.pix.width = VIDEO_WIDTH; fmt.fmt.pix.height = VIDEO_HEIGHT; fmt.fmt.pix.pixelformat = V4L2_PIX_FMT_RGB565; //要与摄像头相对应, 视频数据存储类型,例如是YUV4:2:2还是RGB fmt.fmt.pix.depth = 16; if(ioctl(cam_fd, VIDIOC_S_FMT,&fmt) < 0){ printf("set format is fail!! \n"); exit(4); } /* * open framebuffer device */ if ((fb_device = getenv("FRAMEBUFFER")) == NULL) fb_device = FB_DEV; fbdev = fb_open(fb_device); /* * get status of framebuffer device */ fb_stat(fbdev, &fb_width, &fb_height, &fb_depth); if ((VIDEO_WIDTH > fb_width) || (VIDEO_HEIGHT > fb_height)) return (-1); /* * map framebuffer device to shared memory */ screensize = fb_width * fb_height * fb_depth / 8; fbmem = fb_mmap(fbdev, screensize); /*以上步骤完成了视频采集的准备工作,但驱动还没有启动采集过程, 应用程序需要调用VIDIOC_STREAMON ioctl 系统调用驱动才会开始采集数据。 enum v4l2_buf_type type = V4L2_BUF_TYPE_VIDEO_CAPTURE; ioctl (fd, VIDIOC_STREAMON, &type);*/ //开始采集视频 int buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE; if(ioctl(cam_fd,VIDIOC_STREAMON,&buf_type) < 0){ printf("VIDIOC_STREAMON is fail!! \n"); exit(9); } /*采集过程开始以后,驱动会不停地将数据写入分配的缓冲区内, 当一个缓冲区的数据准备就绪后,驱动就会将其放入输出队列,等待应用程序的处理。 当所有的缓冲区都进入输出队列后,驱动将停止采集,并等待缓冲区重新放入采集队列。 读取数据时,首先需要将一个缓冲区出队列: struct v4l2_buffer buf; ioctl (fd, VIDIOC_DQBUF, &buf);*/ //取出FIFO 缓存中已经采样的帧缓存, int i = 0; while(i < 1000){ char* buffer = (char*) calloc(VIDEO_WIDTH * VIDEO_HEIGHT*2 ,1); int count = read(cam_fd,buffer,VIDEO_WIDTH * VIDEO_HEIGHT *2); printf(">> %d\n",count); for(y = 0;y < VIDEO_HEIGHT;y++){ memcpy(fbmem + y * fb_width * 2,buffer + y * VIDEO_WIDTH * 2,VIDEO_WIDTH * 2); } nResult = read(fd,&event,sizeof(event)); if(nResult==sizeof(event)){ printf("keycode:%d,keyvalue:%d\n",event.code,event.value); write_jpeg_file( "cemara.jpg"); break; } i++; } //停止视频的采集 if(ioctl(cam_fd,VIDIOC_STREAMOFF,&buf_type) < 0){ printf("VIDIOC_STREAMOFF is fail!! \n"); exit(12); } close(cam_fd); close(fbdev); close(fd); return 0; }