rtml://
进行远程工作状态的监控FFmpeg -f dshow -i video="... -f mpegts -f flv "rtmp://20878....
形式尝试将实时帧图像,另外输出到硬盘固定图片文件, 内容动态变化,
命令改变为: ffmpeg -f image2 -loop 1 -i "path/2/frame.png" ...
但是, 无论怎么调整参数,都只能工作十多帧就崩溃了, 报错都是类似:
...
Error while decoding stream #0:0: Invalid data found when processing input
Last message repeated 1 times
Past duration 0.799995 too large
[flv @ 0x7fabfa001800] Failed to update header with correct duration.34.3kbits/s dup=0 drop=1120 speed=7.25x
[flv @ 0x7fabfa001800] Failed to update header with correct filesize.
frame= 1730 fps=109 q=5.5 Lsize= 3300kB time=00:01:55.40 bitrate= 234.3kbits/s dup=0 drop=1120 speed=7.24x
video:3273kB audio:0kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.832250%
而将帧图像持续输出为一系列有命名规模的静态图片后, 参考:
ffmpeg -f image2 -framerate 12 -i foo-%03d.jpeg -s WxH foo.avi
ffmpeg -f image2 -pattern_type glob -framerate 12 -i 'foo-*.jpeg' -s WxH foo.avi
ffmpeg -i frame_%d.jpg -c:v copy rotated.avi
无论怎么折腾参数, 都无法工作, 报错为:
...
Metadata:
encoder : Lavf57.71.100
Stream #0:0: Video: flv1 (flv) ([2][0][0][0] / 0x0002), yuv420p, 480x270, q=2-31, 200 kb/s, 25 fps, 1k tbn, 25 tbc
Metadata:
encoder : Lavc57.89.100 flv
Side data:
cpb: bitrate max/min/avg: 0/0/200000 buffer size: 0 vbv_delay: -1
[flv @ 0x7ff53d008600] Failed to update header with correct duration.
[flv @ 0x7ff53d008600] Failed to update header with correct filesize.
frame= 20 fps=0.0 q=9.7 Lsize= 173kB time=00:00:00.76 bitrate=1867.3kbits/s speed=10.1x
video:173kB audio:0kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.300397%
所以, 综合以上, 想知道如何能通过动态图片 /实时增长的系列图片 实时编译为 rmtp 直播流?
或是说, 思路上还有什么选择?
问题其实应该是:
如何通过[FFmpeg]将 webcam 实时帧数据合法推送给第3方 rtmp 直播频道?
@Panic 一语中的:
应该就是使用 pipe,先将 png 转成 rgb 格式或 YUV 格式的 rawvideo, 再送到 ffmpeg 的 pipe 进行编码,输出 rtmp 到...
回顾之前收集到的有关文章:
重新构建了测试脚本实现了实时推送, 延时也在容忍范畴之内 ;-)
命令参数一定要有:
, '-f', 'rawvideo'
, '-vcodec','rawvideo'
对应的, 要将 cv2 处理的图片格式, 从 numpy.ndarray->cv2.cv.cvmat
才能使用 .tostring()
通过 stdin
丢给 FFmpeg 完成格式化并推送
大家的各种质疑, 主要还是系统架构的决策问题:
同时在尝试其它渠道来提问, 但是 V2Ex 的响应最快, 最多...
实在是...
C'est la vie (´-ι_-`)
1
contmonad 2018-03-08 21:47:33 +08:00
经过磁盘文件中转后实时性不好吧,直接用 pipe。这里有个 OpenCV 到 FFmpeg 的例子: https://stackoverflow.com/q/36422211/3107204
我猜用 FFmpeg 的 Python binding 也可以( libavdevice 操作摄像头,libavformat 转封装),而且自由度更高。 |
2
contmonad 2018-03-08 21:51:17 +08:00
你帖子中的描述概念错误好多啊。。建议找 H.264 和 RTMP 的规范看一下
|
3
wdlth 2018-03-08 22:11:37 +08:00 via Android
为何不直接传输视频流?
|
4
likuku 2018-03-08 22:55:11 +08:00
rtmp 传输的也就是包装成 flv 的 h264 流 (video: h264, audio: aac)
|
5
likuku 2018-03-08 22:56:38 +08:00
ffmpeg 本身就具有直接读取摄像头抓取信息的能力,只要你机器编码足够快(GPU 之类加速就 OK),实时推流不是问题
|
6
fgodt 2018-03-08 22:59:21 +08:00 via Android
不是很懂你的构架,正常的如果有图片源用 ffmpeg 编成 264 封装成 flv 输出到 rtmp 地址就行了
|
7
picone 2018-03-09 01:13:28 +08:00
动态图片不可行,刚好我毕设在做相关的项目,可以一起讨论。
因为是本科生的毕设,所以就用动态图片实现了,websocket+protobuf,传输图片,前端 img 加载。 后端用 APS 定时抓帧,用 jpeg 编码再推送出去。 我的 mac 跑,9fps,单核 cpu 跑满。。。再高的 fps 就有延迟了。。。 https://github.com/picone/RealTimeTrackingCamera 你可以用 jsmpeg 实现以下,把视频用 mpeg 压缩,效果会好很多 |
8
ETiV 2018-03-09 02:26:39 +08:00
// 可能需要重写 Python 的部分
摄像头 -> FFmpeg -> nginx-rtmp -> 通过指令 push 把直播流推出去 -> 直播站点 \-> Python (或 FFmpeg )读 rtmp:// 直播流,拆出来图片 -> Python 分析 |
10
ZoomQuiet OP |
12
ZoomQuiet OP |
14
ZoomQuiet OP |
15
ZoomQuiet OP @contmonad 再次感谢
pipe 是个靠谱的方向, 之前实现过, 都忘记了... > ... libavdevice 操作摄像头,libavformat 转封装... 涉及 FFmpeg 底层 C 库了,这种调试起来就嗯哼了... |
16
gggxxxx 2018-03-09 09:01:18 +08:00
几年前我自己用 librtmp 做过类似的,摄像头画面直接推到 rtmp 服务器。
不用 ffmpeg 也能实现。 |
17
fgodt 2018-03-09 09:34:05 +08:00
你想不写代码用几个命令来处理还是有点难度,正确的流程应该是
1 视频流->ffmpeg->pkt 2 pkt->ffmpeg->图片->py 处理 3 pkt->ffmpeg->rtmp 第二步第三步可以互不影响 |
18
Panic 2018-03-09 10:07:19 +08:00
应该就是使用 pipe,先将 png 转成 rgb 格式或 YUV 格式的 rawvideo, 再送到 ffmpeg 的 pipe 进行编码,输出 rtmp 到添加了 rtmp 模块的 nginx 服务器。客户端连接通过 rtmp 链接访问 nginx 就可以了。
|
19
retamia 2018-03-09 10:44:19 +08:00
你是要将摄像头采集到的图片帧处理后,进行直播推流吗?
|
20
ZoomQuiet OP |
22
ZoomQuiet OP @gggxxxx 是也乎 ╮(╯▽╰)╭
已在看此模块 官方样例是从 rmtp 流拿帧的… 但文档中说能写… 但只接受 flv 封装的图片… 然有…找不到可用的… flv 封装模块 所以…你之前是乍写入上游直播流的? |
24
ZoomQuiet OP |
25
fqxyhdsy 2018-03-19 14:47:50 +08:00
@ZoomQuiet 您好,楼主!请问你这问题解决了吗!现在因为业务需求也要弄个类似的!这边现在的情况是,直播流通过 ffmpeg 切帧,将切完的帧存放在了服务器某个文件夹下,然后不停的覆盖该文件。应该就是您上面说的动态固定图片那种情况。请问具体如何结合 pipe,将这个动态固定图片推成一个视频流!刚接触 python 没多久,请详细讲解一哈!谢谢!
|
26
fqxyhdsy 2018-03-20 15:05:04 +08:00
@picone 您好!请问,动态图片+websocket+protobuf,这种方案怎么用 protobuf 来传输图片呀? 这边之前的解决方案是 socket 传输 base64 数据,前端用 websocket 接受数据然后绑定图片到视图层。但是太吃内存了,服务器承受不了!求解惑!万分感谢!
|
27
picone 2018-03-20 15:49:04 +08:00
@fqxyhdsy #26 不要转 base64 了,直接把图片 jpeg 编码,然后直接使用 protobuf 序列化就 OK 了,protobuf 接受二进制。如果是连续动态的图片,建议用 mpeg 编码
|
28
fqxyhdsy 2018-03-20 16:04:07 +08:00
@picone 首先万分感谢回复! 如果将 jpeg(mpeg)编码后的图片用 protobuf 序列化传过去,应该是没问题。但是现在前端是用 js 的 websocket 来链接的!那怎么来反序列化 protobuf 传过来的数据呢! js 这边是否能够支持 protobuf 和 jpeg(mpeg)解码!刚接触没多久,万分包涵!
|
30
ZoomQuiet OP @fqxyhdsy 是也乎 ╮(╯▽╰)╭
不好意思才看到… 已有流的话… FFmpeg 本身就支持: - 拖流为视频文件 - 或直接转播推流到其它协议流 进一步的…图片序列少 TPS 信息…体积也大… 不如存为 .mkv 需要时 --> 推为流 |
31
liu826250634 2018-08-21 19:27:14 +08:00
题主您好。
我也是遇到这样的问题,需要从海康摄像头抓取之后进行人脸识别,对视频进行处理之后进行 rtmp 进行推流。 我的代码: size = (int(cap.get(cv2.CAP_PROP_FRAME_WIDTH)), int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))) sizeStr = str(size[0]) + 'x' + str(size[1]) fps = cap.get(cv2.CAP_PROP_FPS) # 30p/self fps = int(fps) rtmpUrl = 'rtmp://192.168.1.71:1935/live/app' command = ['ffmpeg', '-y', '-f', 'rawvideo', '-vcodec','rawvideo', '-pix_fmt', 'bgr24', '-s', sizeStr, '-r', str(fps), '-i', '-', '-c:v', 'libx264', '-pix_fmt', 'yuv420p', '-preset', 'ultrafast', '-f', 'flv', rtmpUrl] while True: ret, frame = cap.read() proc = sp.Popen(command, stdin=sp.PIPE, shell=False) proc.stdin.write(frame.tostring()) if cv2.waitKey(1) & 0xFF == ord('q'): break 运行是成功了(也不能说成功,有时候会崩溃),但是用 VLC 却是不能拉流观看。 然后再想是否是你说的这个问题,从 numpy.ndarray->cv2.cv.cvmat。 但是在网上查资料说 mat_array = cv2.cv.fromarray(frame),这个 opencv-python 2.4 之后就没了。 希望题主看到之后能解答一下! |
32
ZoomQuiet OP |
33
ZoomQuiet OP @liu826250634 是也乎,( ̄▽ ̄)
这也是为什么, 我们一直没升级到 Py3+cv3 的原因, py2.7.X+OpenCV2.4.X 的组合足够安定就没理由升级到可能更好的体系... 另外, VLC 版本也有不同的问题. 建议参考 FFmpeg 官方文档, 先用 ffplayer 来检验 rmtp 是否真正推流成功... 以及, 俺的经验, 这个 rmtp 最好还是先走 腾讯云的视频流服务, 完成一个安定的数据流.... 否则, 本地局网的情况太复杂....不好判定 |
34
hellotiny 2019-03-26 11:31:12 +08:00
博主你好啊,我也遇到这个问题,不太理解基于 pipe 进行数据共享推流的这个原理,想问逻辑问题。
通过管道的方式实现的哪一种形式呢? 一是将处理过的图片缓存进 buff 中形成了有顺序的帧形成的视频流,使用 ffmpeg 推出的就是 buff 中缓存的视频流吗? 那么推流时抓图和处理图片的进程会不会暂停? 二是处理一帧放入管道,然后就通过 ffmpeg 推送一帧到 rtmp 服务器吗? 我没办法判断我通过 pipe 推流有没有成功,我在 RTMP 播放器中输入推流的 RTMP 地址是没有直播在播放的。 |