将原始 OpenCV 图像传输到 FFmpeg

2024-11-08 08:43:00
admin
原创
225
摘要:问题描述:这是一个使用 OpenCV 的 python 绑定读取网络摄像头的相当简单的例子:'''capture.py''' import cv, sys cap = cv.CaptureFromCAM(0) # 0 is for /dev/video0 while Tr...

问题描述:

这是一个使用 OpenCV 的 python 绑定读取网络摄像头的相当简单的例子:

'''capture.py'''
import cv, sys
cap = cv.CaptureFromCAM(0)                    # 0 is for /dev/video0
while True :
    if not cv.GrabFrame(cap) : break
    frame = cv.RetrieveFrame(cap)
    sys.stdout.write( frame.tostring() )

现在我想将输出通过管道传输到 ffmpeg,如下所示:

$ python capture.py | ffmpeg -f image2pipe -pix_fmt bgr8 -i - -s 640x480 foo.avi

遗憾的是,我无法正确使用 ffmpeg 魔法咒语,并且它失败了

  libavutil 50.15.1 / 50.15.1
  libavcodec 52.72.2 / 52.72.2
  libav 格式 52.64。 2 / 52.64。 2
  libavdevice 52.2.0 / 52.2.0
  libavfilter 1.19.0 / 1.19.0
  libswscale 0.11. 0 / 0.11. 0
  libpostproc 51. 2. 0 / 51. 2. 0
输出 #0,avi,至‘out.avi’:
    流 #0.0:视频:flv、yuv420p、640x480、q=2-31、19660 kb/s、90k tbn、30 tbc
[image2pipe @ 0x1508640]已达到max_analyze_duration
[image2pipe @ 0x1508640]根据比特率估算时长,可能不准确
输入 #0,image2pipe,来自‘pipe:’:
  时长:N/A,比特率:N/A
    流 #0.0:视频:0x0000、bgr8、25 fps、25 tbr、25 tbn、25 tbc
swScaler:0x0 -> 640x480 是无效的缩放尺寸
  • 捕获的帧肯定是 640x480。

  • 我很确定 OpenCV 图像类型 (IplImage) 的像素顺序是 GBR,即每个通道一个字节。至少,这似乎是从相机中传出来的。

我不是 ffmpeg 专家。有人成功完成过这个吗?


解决方案 1:

经过一番折腾,我终于使用 FFmpeg rawvideo 解复用器解决了这个问题:

python capture.py | ffmpeg -f rawvideo -pixel_format bgr24 -video_size 640x480 -framerate 30 -i - foo.avi

由于原始视频中没有指定假定视频参数的标题,因此用户必须指定这些参数才能正确解码数据:

  • -framerate设置输入视频帧率。默认值为 25。

  • -pixel_format设置输入视频像素格式。默认值为yuv420p。

  • -video_size设置输入视频大小。没有默认值,因此必须明确指定此值。

这里还有一些针对高级用户的额外内容。同样的事情,但使用 VLC 将实时输出流式传输到网络,Flash 格式:

python capture.py | cvlc --demux=rawvideo --rawvid-fps=30 --rawvid-width=320 --rawvid-height=240  --rawvid-chroma=RV24 - --sout "#transcode{vcodec=h264,vb=200,fps=30,width=320,height=240}:std{access=http{mime=video/x-flv},mux=ffmpeg{mux=flv},dst=:8081/stream.flv}"

编辑:使用 ffmpeg 和 ffserver 创建 webm 流

python capture.py | ffmpeg -f rawvideo -pixel_format rgb24 -video_size 640x480 -framerate 25 -i - http://localhost:8090/feed1.ffm

解决方案 2:

我有点迟了,但我强大的VidGearPython 库可以自动在任何平台上将 OpenCV 帧传输到 FFmpeg 中。这是一个基本的 Python 示例:

# import libraries
from vidgear.gears import WriteGear
import cv2

output_params = {"-vcodec":"libx264", "-crf": 0, "-preset": "fast"} #define (Codec,CRF,preset) FFmpeg tweak parameters for writer

stream = cv2.VideoCapture(0) #Open live webcam video stream on first index(i.e. 0) device

writer = WriteGear(output_filename = 'Output.mp4', compression_mode = True, logging = True, **output_params) #Define writer with output filename 'Output.mp4' 

# infinite loop
while True:
    
    (grabbed, frame) = stream.read()
    # read frames

    # check if frame empty
    if not is grabbed:
        #if True break the infinite loop
        break
    

    # {do something with frame here}
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

    # write a modified frame to writer
    writer.write(gray) 
       
    # Show output window
    cv2.imshow("Output Frame", frame)

    key = cv2.waitKey(1) & 0xFF
    # check for 'q' key-press
    if key == ord("q"):
        #if 'q' key-pressed break out
        break

cv2.destroyAllWindows()
# close output window

stream.release()
# safely close video stream
writer.close()
# safely close writer

来源:https ://abhitronix.github.io/vidgear/latest/gears/writegear/compression/usage/#using-compression-mode-with-opencv

您可以查看VidGear Docs以了解更多高级应用程序和功能。

希望有帮助!

解决方案 3:

不确定这是 Mac OS 特有的还是 python3 特有的,但我需要将框架转换为字符串才能使其为我工作,如下所示:

sys.stdout.write(str(frame.tostring()))

解决方案 4:

我花了一个小时才弄清楚,默认情况下,Windows 管道不是二进制的。这会导致某些字节(特别是换行符)被修改/省略,并且由于帧大小不稳定,因此生成的视频会缓慢移动。

为了解决这个问题,修改后的 python 文件:

"""
videoCapture.py
"""
import cv2, sys
import time

if sys.platform == "win32":
    import os, msvcrt
    msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY)

cap = cv2.VideoCapture(0)                    # 0 is for /dev/video0
while True :
    ret, frm = cap.read()
    sys.stdout.write( frm.tostring() )

要测试管道传输原始视频是否成功,请使用 ffplay。请确保您指定的帧速率高于管道传输的帧速率,否则视频将开始滞后

python videoCapture.py | ffplay -f rawvideo -pix_fmt bgr24 -s 640x480 -framerate 40 -i -

解决方案 5:

如果传递 bgr8 OpenCV 帧,仍然需要-pix_fmt bgr24在 FFmpeg 管道中进行设置。

相关推荐
  政府信创国产化的10大政策解读一、信创国产化的背景与意义信创国产化,即信息技术应用创新国产化,是当前中国信息技术领域的一个重要发展方向。其核心在于通过自主研发和创新,实现信息技术应用的自主可控,减少对外部技术的依赖,并规避潜在的技术制裁和风险。随着全球信息技术竞争的加剧,以及某些国家对中国在科技领域的打压,信创国产化显...
工程项目管理   1565  
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1354  
  信创国产芯片作为信息技术创新的核心领域,对于推动国家自主可控生态建设具有至关重要的意义。在全球科技竞争日益激烈的背景下,实现信息技术的自主可控,摆脱对国外技术的依赖,已成为保障国家信息安全和产业可持续发展的关键。国产芯片作为信创产业的基石,其发展水平直接影响着整个信创生态的构建与完善。通过不断提升国产芯片的技术实力、产...
国产信创系统   21  
  信创生态建设旨在实现信息技术领域的自主创新和安全可控,涵盖了从硬件到软件的全产业链。随着数字化转型的加速,信创生态建设的重要性日益凸显,它不仅关乎国家的信息安全,更是推动产业升级和经济高质量发展的关键力量。然而,在推进信创生态建设的过程中,面临着诸多复杂且严峻的挑战,需要深入剖析并寻找切实可行的解决方案。技术创新难题技...
信创操作系统   27  
  信创产业作为国家信息技术创新发展的重要领域,对于保障国家信息安全、推动产业升级具有关键意义。而国产芯片作为信创产业的核心基石,其研发进展备受关注。在信创国产芯片的研发征程中,面临着诸多复杂且艰巨的难点,这些难点犹如一道道关卡,阻碍着国产芯片的快速发展。然而,科研人员和相关企业并未退缩,积极探索并提出了一系列切实可行的解...
国产化替代产品目录   28  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用