2013-02-22 34 views
6

Làm cách nào để chụp ảnh bằng webcam của tôi bằng C++ và lưu vào đĩa? Tôi không thể sử dụng OPENCV do vấn đề phần cứng. Webcam webcam hoạt động với các chương trình khác như mplayer, pho mát, gpicview, ffmpeg, v.v.Chụp ảnh webcam USB trong C++ KHÔNG openCV (LINUX)

Tôi nghe V4L có khả năng thực hiện việc này, nhưng có thư viện C++ nào không? Ai có thể cho tôi xem ví dụ về C++ về cách thực hiện điều này không?

+0

Chào mừng bạn đến với Stack Overflow! StackOverflow không phải là nơi thích hợp cho câu hỏi này. Chúng tôi không viết mã cho bạn. Bạn cần phải viết mã của riêng bạn và nếu bạn không chắc chắn tại sao một cái gì đó không hoạt động như mong đợi, hãy đăng mã với lời giải thích về những gì bạn đang mong đợi, và những gì nó thực sự làm bao gồm tất cả các thông báo lỗi. Xem [về StackOverflow] (http://stackoverflow.com/about). –

Trả lời

18

Nó khá dễ dàng, bạn có thể làm read trên máy quay video, sau khi bạn đã kích hoạt một số ioctls để có được cam dưới sự kiểm soát của bạn.

Bạn có thể sử dụng v4l2 cho công việc này. Bạn làm điều này trong những bước sau:

  1. Mở tin thiết bị của máy ảnh (thường là "/ dev/video0")
  2. Nói v4l2 mà bạn muốn biết một số khả năng của thiết bị
  3. Nói v4l2 đọc từ thiết bị
  4. Nói với định dạng Mà v4l2 bạn muốn sử dụng

Dưới đây là một việc thực hiện tôi sử dụng cho công việc này. Nó sẽ đặt camera để quay video ở 320x240 Pixel, nhưng bạn có thể đọc các độ phân giải, máy ảnh có khả năng từ cấu trúc v4l2_capability.

Ngoài ra tôi đã không kiểm tra mã trên ảnh khác so với PS2 EyeToy của tôi, nhưng nó là chủ yếu lấy từ một chương trình mẫu tên qv4l2 (bạn có thể lấy nó từ here). Chương trình này sẽ giải quyết tất cả các vấn đề khác mà bạn thường thấy ở đó.

#include <stdio.h> 
#include <unistd.h> 
#include <stdlib.h> 
#include <string.h> 
#include <fcntl.h>    /* low-level i/o */ 
#include <errno.h> 
#include <sys/stat.h> 
#include <sys/types.h> 
#include <sys/time.h> 
#include <sys/ioctl.h> 

#include <linux/videodev2.h> 

static int xioctl(int fh, int request, void *arg) 
{ 
    int r; 
    do { 
     r = ioctl(fh, request, arg); 
    } while (-1 == r && EINTR == errno); 
    return r; 
} 

int allocCamera(const char* file) 
{ 
    struct v4l2_capability cap; 
    struct v4l2_crop crop; 
    struct v4l2_format fmt; 

    int camera_fd = open(file, O_RDONLY); 

    if (-1 == xioctl (camera_fd, VIDIOC_QUERYCAP, &cap)) { 
     if (EINVAL == errno) { 
      fprintf (stderr, "%s is no V4L2 device\n", file); 
      exit (EXIT_FAILURE); 
     } else { 
      printf("\nError in ioctl VIDIOC_QUERYCAP\n\n"); 
      exit(0); 
     } 
    } 

    if (!(cap.capabilities & V4L2_CAP_VIDEO_CAPTURE)) { 
     fprintf (stderr, "%s is no video capture device\n", file); 
     exit (EXIT_FAILURE); 
    } 

    if (!(cap.capabilities & V4L2_CAP_READWRITE)) { 
     fprintf (stderr, "%s does not support read i/o\n", file); 
     exit (EXIT_FAILURE); 
    } 

    memset(&fmt, 0, sizeof(fmt)); 
    fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; 
    fmt.fmt.pix.width  = 320; 
    fmt.fmt.pix.height  = 240; 
    fmt.fmt.pix.pixelformat = V4L2_PIX_FMT_YUYV; 
    fmt.fmt.pix.field  = V4L2_FIELD_INTERLACED; 
    if (-1 == xioctl(camera_fd, VIDIOC_S_FMT, &fmt)) { 
     printf("VIDIOC_S_FMT"); 
    } 
    return camera_fd; 
} 
+0

Cảm ơn bạn đã trả lời chi tiết, tôi sẽ thử. – Prem