Bilder von Webcam lesen
-
Hallo,
ich habe aus einem Buch einen Code um von der Webcam ein Bild abzuspeichern.
An sich funkt es auch, jedoch ist das Bild schwarz/weiß und wird in dreifacher Ausführung abgespeichert (eventuell RGB)
Das verstellen des Kontrast/Helligkeit funkt prima.Das Prog wird wie folgt aufrufen progrname > bild.ppm
#include <stdio.h> #include <unistd.h> #include <fcntl.h> #include <sys/ioctl.h> #include <linux/videodev.h> int height; int width; int Kontrast; int Helligkeit; /*#############################################################################*/ int main(int argc, char *argv[]) { int fd; long MAX_BYTES; long length; struct video_window video_win; struct video_picture video_pict; Kontrast = 70; Helligkeit = 70; height = 480; width = 640; MAX_BYTES = height * width * 3; unsigned char image[MAX_BYTES]; if ((fd = open("/dev/video", O_RDONLY)) == -1) { perror("read_image: Can't open device"); return(1); } /*------------------------------------------------------*/ if (ioctl(fd, VIDIOCGWIN, &video_win) == -1) { perror("read_image: Can't get video window"); return(1); } video_win.width = width; video_win.height = height; if (ioctl(fd, VIDIOCSWIN, &video_win) == -1) { perror("write_image: Can't put video window"); return(1); } /*------------------------------------------------------*/ if (ioctl(fd, VIDIOCGPICT, &video_pict) == -1) { perror("read_pic: Can't get picture information"); return(1); } video_pict.depth = 16; // video_pict.palette = VIDEO_PALETTE_RGB24; video_pict.brightness = 0.5 + 655.35 * Helligkeit; video_pict.contrast = 0.5 + 655.35 * Kontrast; if (ioctl(fd, VIDIOCSPICT, &video_pict) == -1) { perror("write_pic: Can't put picture information"); return(1); } /*------------------------------------------------------*/ length = video_win.width * video_win.height * 3; if (length > MAX_BYTES) { fprintf(stderr, "read_image: Image too large.\n"); return(1); } if (read(fd, image, length) == -1) { perror("read_image: Error while reading"); return(1); } close(fd); printf("P6\n%d %d\n255\n", video_win.width,video_win.height); fwrite(image, 3, video_win.width * video_win.height, stdout); return(0); }
Danke
worst_case
-
Du stellst die Farbtiefe auf 16 Bit (also 2 Byte) mit der Anweisung "
video_pict.depth = 16;
". Die PPM-Datei ist aber so aufgebaut, dass 3 Byte pro Pixel (RGB) erwartet werden, also 24 Bit. Das muss zu einem merkwürdigen Bild führen.
Leider sind meine Erfahrungen so, dass sich die Tiefe nicht bei allen WebCams (Treibern) für das Auslesen mit fread() einstellen lässt. Bessere Erfahrungen habe ich mit mmap() gemacht. (Wie's geht, steht in meinem Buch "C und Linux") Bei manchen Treibern (z.B. qcam.o und pwc.o) lässt sich die Default-Bitbreite beim Starten des Moduls mit "insmod" als Option vorgeben.Auf meiner Hompage (s.u.) findest du ein Programm zum Darstellen der WebCam unter X11 als Quelltext und als Binary.
Martin