1. 程式人生 > >Linux V4L2採集YUV視訊並播放

Linux V4L2採集YUV視訊並播放

接著上一接部落格繼續寫。

採集YUV視訊很簡單,比採集bmp圖片更簡單,因為採集圖片還要考慮圖片格式,要做YUV到RGB的格式轉換等工作。而採集YUV視訊直接把採集的YUV資料丟進一個檔案裡就行了。

在上一篇部落格裡,修改一點點程式碼就可以完成採集YUV視訊的工作了。

static int readfram()
{
    struct pollfd pollfd;
    int ret,i;
    char filename[50];
for(;;){
        memset(&pollfd, 0, sizeof(pollfd));
        pollfd.fd = fd;
        pollfd.events = POLLIN;
        ret = poll(&pollfd, 1
, 800); if(-1 == ret){ perror("VIDIOC_QBUF fail.\n"); return -1; }else if(0 == ret){ printf("poll time out\n"); continue; } printf("-------------poll success---------------\n"); // static struct v4l2_buffer buf; if
(pollfd.revents & POLLIN){ memset(&buf, 0, sizeof(buf)); buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; buf.memory = V4L2_MEMORY_MMAP; ret = ioctl(fd, VIDIOC_DQBUF, &buf); if(0 != ret){ perror("VIDIOC_QBUF fail.\n"); return -1; } //v4l2_buffer // 直接儲存的yuyv資料的視訊 ret = fwrite((char*)
framebuf[buf.index].start, 1, buf.length, file); // RGB格式資料的bmp圖片 /* starter = (unsigned char*)framebuf[buf.index].start; newBuf = (unsigned char*)calloc((unsigned int)(framebuf[buf.index].length*3/2),sizeof(unsigned char)); yuv422_2_rgb(); create_bmp_header(); //yuyv422toBGRY(starter); sprintf(filename,"rgb%d.bmp",i); FILE *file1 = fopen(filename, "wb"); fwrite(&bfh,sizeof(bfh),1,file1); fwrite(&bih,sizeof(bih),1,file1); fwrite(newBuf, 1, buf.length*3/2, file1); //fwrite(rgb, 1, width*height*3, file1); fclose(file1); */ ret = ioctl(fd, VIDIOC_QBUF, &buf); } } return ret; }

僅僅把readfram()函式做了一點修改,然後開啟和關閉在這個檔案在main()函式中完成。

file = fopen(YUV_VIDEO, "wa+");
readfram();
fclose(file);

原始碼可以從我的git上下載:
“`
git clone https://github.com/zhangdalei/v4l2-.git
···
和上一節部落格一樣,採集視訊的程式碼也是不能再PC上正常執行,採集的視訊有條紋等各種問題,在我的開發版上可以正常使用,採集的視訊可以正常播放。
採集的視訊格式是.yuv格式,使用的播放器是pYUV。在使用這個播放器是,開啟視訊時會設定一些選項,這是設定介面的截圖:
這裡寫圖片描述

圖片裡最後一行有兩個可勾選的選項,第一項是Interleaved,這是必須要勾選,不然播放會有問題。這叫做隔行掃描,因為在應用中設定視訊格式是就設定的隔行掃描。

播放效果:
這裡寫圖片描述