【GStreamer实战】从USB相机到文件:一站式掌握图片抓取与视频录制

张开发
2026/4/21 17:22:54 15 分钟阅读
【GStreamer实战】从USB相机到文件:一站式掌握图片抓取与视频录制
1. 环境准备与设备检测第一次接触GStreamer处理USB相机时我最头疼的就是环境配置问题。记得有次在Jetson TX2上折腾了整整两天才发现是缺少了v4l-utils工具包。为了避免大家重蹈覆辙这里分享几个关键检查点。首先用lsb_release -a确认系统版本。我在Ubuntu 18.04和20.04上都测试过建议使用官方支持的LTS版本。接着安装核心工具包sudo apt-get install gstreamer1.0-tools gstreamer1.0-plugins-good \ gstreamer1.0-plugins-bad v4l-utils检测USB相机是否被系统识别ls /dev/video*如果看到类似/dev/video0的设备节点说明硬件连接正常。我遇到过USB3.0接口供电不足导致设备时断时续的情况换成带外接电源的Hub就解决了。用v4l2-ctl查看相机能力v4l2-ctl --device/dev/video0 --list-formats-ext这个命令会列出相机支持的分辨率和格式。比如我的罗技C920输出是这样的Pixel Format: MJPG (compressed) Size: 1920x1080 (30 fps) Size: 1280x720 (30 fps) Pixel Format: YUYV Size: 640x480 (30 fps)注意MJPG格式通常能支持更高分辨率而YUYV格式在相同分辨率下帧率可能更低。实际项目中我建议先用MJPG格式获取高清画面需要原始数据时再切到YUYV。2. 静态图片抓取实战2.1 捕获YUV格式图片先看最简单的单帧抓取命令gst-launch-1.0 v4l2src device/dev/video0 num-buffers1 \ ! video/x-raw,formatYUY2,width640,height480,framerate30/1 \ ! jpegenc ! filesink locationtest.jpg这个管道的工作流程是v4l2src从/dev/video0获取1帧数据指定格式为640x480的YUYV原始数据jpegenc编码器转换为JPEG格式保存到test.jpg文件我经常遇到的问题是格式不匹配。比如相机实际输出是MJPG但管道里指定了YUYV这时会报错ERROR: from element /GstPipeline:pipeline0/GstV4l2Src:v4l2src0: Internal data stream error.解决方法是在v4l2src后立即用capfilter指定正确格式! image/jpeg,width1280,height720 ! jpegdec \ ! video/x-raw,formatYUY2 ! jpegenc2.2 批量抓图技巧做数据集采集时需要连续抓图可以用multifilesinkgst-launch-1.0 v4l2src device/dev/video0 \ ! image/jpeg,width1280,height720,framerate30/1 \ ! jpegdec ! videorate ! video/x-raw,framerate1/1 \ ! jpegenc ! multifilesink locationframe%03d.jpg这里videorate组件将帧率降到1fps每秒钟保存1张图片。我在做物体识别训练集时这个技巧帮了大忙。3. 视频录制方案对比3.1 AVI格式录制AVI是经典的容器格式优点是兼容性好gst-launch-1.0 v4l2src device/dev/video0 \ ! image/jpeg,width1280,height720,framerate30/1 \ ! queue ! avimux ! filesink locationoutput.avi但实际测试发现直接保存MJPG流的AVI文件在Windows播放器可能有兼容问题。更稳妥的做法是统一解码再编码! jpegdec ! videoconvert ! jpegenc ! avimux3.2 MP4(H.264)高清录制H.264编码能大幅减小文件体积。这是我最常用的方案gst-launch-1.0 v4l2src device/dev/video0 \ ! video/x-raw,formatYUY2,width1280,height720,framerate30/1 \ ! videoconvert ! x264enc bitrate2000 tunezerolatency \ ! mp4mux ! filesink locationoutput.mp4关键参数说明bitrate控制码率单位kbpszerolatency减少编码延迟必须包含videoconvert确保格式兼容在Jetson平台上可以启用硬件加速! omxh264enc ! video/x-h264,profilehigh4. 高级应用技巧4.1 预览录制同步方案使用tee组件实现一源多路gst-launch-1.0 v4l2src device/dev/video0 \ ! image/jpeg,width1280,height720,framerate30/1 \ ! tee namet t. ! queue ! jpegdec ! autovideosink \ t. ! queue ! jpegdec ! x264enc ! mp4mux \ ! filesink locationrecord.mp4注意点每条分支都要有独立的queue预览分支用autovideosink自动选择显示方式录制分支建议设置syncfalse避免丢帧4.2 音视频同步录制如果相机带麦克风可以这样录制gst-launch-1.0 v4l2src device/dev/video0 \ ! image/jpeg,width640,height480,framerate30/1 \ ! tee namevideo \ pulsesrc ! audioconvert ! audioresample ! queue ! voaacenc \ ! mux. \ video. ! queue ! jpegdec ! x264enc ! mux. \ mp4mux namemux ! filesink locationav.mp44.3 网络流媒体推流将视频流推送到RTMP服务器gst-launch-1.0 v4l2src device/dev/video0 \ ! video/x-raw,formatYUY2,width640,height480,framerate30/1 \ ! videoconvert ! x264enc bitrate1000 tunezerolatency \ ! flvmux ! rtmpsink locationrtmp://example.com/live/stream在Jetson平台上开发时记得监控GPU温度tegrastats长时间录制建议加散热风扇我遇到过因为过热导致编码失败的情况。

更多文章