3. 摄像头选型与接入:USB摄像头驱动、网络摄像头RTSP地址解析、摄像头参数配置

摄像头选型这件事,说简单也简单,说坑也多。我刚开始做流媒体那会儿,觉得随便买个摄像头就能用,结果被驱动兼容性和RTSP地址格式折腾了好几天。今天咱们就把这块彻底捋清楚。

核心要点:摄像头选型决定了推流管线的起点质量。USB摄像头适合本地测试和小规模部署,网络摄像头(IPC)才是生产环境的主力。选型时重点关注:驱动兼容性、RTSP协议支持、分辨率帧率参数。

3.1 USB摄像头驱动与接入

USB摄像头接入Linux系统,核心就是驱动和设备节点。我个人习惯先用 lsusb 确认设备是否被识别。

# 查看USB设备列表
lsusb

# 输出示例:
Bus 001 Device 004: ID 046d:0825 Logitech, Inc. Webcam C270

看到设备ID后,再检查内核是否加载了对应的驱动。大部分UVC(USB Video Class)摄像头会被 uvcvideo 驱动自动识别。

# 检查驱动是否加载
lsmod | grep uvcvideo

# 查看摄像头设备节点
ls /dev/video*

嗯,这里要注意:/dev/video0 是默认节点,但有些摄像头会占用多个节点(比如 /dev/video1 用于元数据)。我遇到过一台海康的USB摄像头,插上后生成了 /dev/video0 和 /dev/video1,结果 video0 是空的,真正的视频流在 video1 上。当时排查了半天,最后用 v4l2-ctl 才确认。

调试技巧:用 v4l2-ctl --list-devices 可以列出所有摄像头设备及其对应的节点,比直接看 /dev/video* 更清晰。

# 查看摄像头支持的格式和分辨率
v4l2-ctl -d /dev/video0 --list-formats-ext

# 输出示例(部分):
ioctl: VIDIOC_ENUM_FMT
        Index       : 0
        Type        : Video Capture
        Pixel Format: 'MJPG' (compressed)
        Name        : Motion-JPEG
                Size: Discrete 1920x1080
                        Interval: 1/30 (0.033 s)
                Size: Discrete 1280x720
                        Interval: 1/30 (0.033 s)

看到这些信息,你就能确定摄像头支持哪些分辨率和帧率。我建议优先选MJPEG格式,因为它压缩后带宽占用小,对CPU压力也低。YUV格式虽然画质好,但数据量太大,推流时容易卡顿。

3.2 网络摄像头RTSP地址解析

网络摄像头(IPC)通过RTSP协议传输视频流。RTSP地址的格式各家厂商都不一样,这是最让人头疼的地方。

RTSP地址的基本结构是:

rtsp://[用户名:密码@]IP地址[:端口]/[路径]

但不同厂商的路径规则完全不同。我整理了一份常见厂商的RTSP地址格式对照表:

厂商 RTSP地址格式 默认端口 备注
海康威视 rtsp://admin:12345@192.168.1.64:554/h264/ch1/main/av_stream 554 主码流;子码流用 sub 替换 main
大华 rtsp://admin:admin@192.168.1.65:554/cam/realmonitor?channel=1&subtype=0 554 subtype=0 主码流,subtype=1 子码流
宇视 rtsp://admin:admin@192.168.1.66:554/video1/1/1 554 路径中的数字表示通道和码流类型
TP-Link rtsp://admin:admin@192.168.1.67:554/stream1 554 stream1 主码流,stream2 子码流
通用ONVIF rtsp://192.168.1.68:554/onvif1 554 部分ONVIF设备使用此格式

避坑指南:我曾经在项目中遇到一个大华的摄像头,RTSP地址死活连不上。后来发现是密码里包含了特殊字符(比如 @ 或 :),导致URL解析错误。解决办法是对特殊字符做URL编码,比如 @ 换成 %40。

验证RTSP地址是否可用,我推荐用 ffprobe 或 ffplay:

# 用ffprobe查看RTSP流信息
ffprobe -rtsp_transport tcp -i "rtsp://admin:12345@192.168.1.64:554/h264/ch1/main/av_stream"

# 用ffplay直接播放测试
ffplay -rtsp_transport tcp -i "rtsp://admin:12345@192.168.1.64:554/h264/ch1/main/av_stream"

这里有个小细节:-rtsp_transport tcp 参数强制使用TCP传输。UDP虽然延迟低,但丢包严重时画面会花掉。我一般先用TCP测试,确认地址没问题后再根据网络环境决定传输协议。

3.3 摄像头参数配置

摄像头参数配置直接影响推流质量。说白了,就是要在画质、延迟、带宽三者之间找平衡。

USB摄像头参数配置主要通过 v4l2-ctl 工具:

# 查看当前参数
v4l2-ctl -d /dev/video0 --all

# 设置分辨率、帧率、像素格式
v4l2-ctl -d /dev/video0 --set-fmt-video=width=1280,height=720,pixelformat=MJPG
v4l2-ctl -d /dev/video0 --set-parm=30

# 设置亮度、对比度、饱和度等
v4l2-ctl -d /dev/video0 --set-ctrl=brightness=128
v4l2-ctl -d /dev/video0 --set-ctrl=contrast=64
v4l2-ctl -d /dev/video0 --set-ctrl=saturation=64

网络摄像头的参数配置通常通过HTTP API或ONVIF协议。以海康为例,它的配置接口是:

# 通过HTTP API设置主码流参数
http://192.168.1.64/ISAPI/Streaming/channels/101/streamConfig

# 请求体示例(XML格式):
<StreamConfig>
  <Video>
    <VideoResolutionWidth>1920</VideoResolutionWidth>
    <VideoResolutionHeight>1080</VideoResolutionHeight>
    <VideoFrameRate>25</VideoFrameRate>
    <VideoBitRate>4096</VideoBitRate>
  </Video>
</StreamConfig>

参数配置建议:

  • 分辨率:1080p是主流,720p用于低带宽场景,4K对编码器压力太大
  • 帧率:25fps(PAL)或30fps(NTFS)足够,低于15fps会有明显卡顿感
  • 码率:H.264编码下,1080p建议2-4Mbps,720p建议1-2Mbps
  • 关键帧间隔:设为帧率的2倍(如25fps设50),太大影响seek响应,太小浪费带宽

你想想看,如果码率设得太低,画面全是马赛克;设得太高,网络带宽扛不住。我一般先按推荐值设置,然后用 ffmpeg 实时查看码率:

# 实时查看推流码率
ffmpeg -rtsp_transport tcp -i "rtsp://admin:12345@192.168.1.64:554/h264/ch1/main/av_stream" \
  -t 10 -f null - 2>&1 | grep "bitrate"

下面这张图总结了摄像头选型与接入的完整流程:

摄像头选型与接入流程 摄像头选型与接入流程 摄像头类型 USB摄像头 网络摄像头(IPC) 驱动检测(lsusb / uvcvideo) 设备节点确认(/dev/video*) 参数配置(v4l2-ctl) RTSP地址解析 地址验证(ffprobe/ffplay) 参数配置(HTTP API / ONVIF) 推流管线接入 两种摄像头最终都汇聚到推流管线

最后说一句,摄像头参数配置不是一次性的。实际部署时,要根据网络状况、客户端数量、编码器性能动态调整。我习惯在配置文件中保留多套参数模板,方便快速切换。