第一次在这里发海报,所以请放轻松。
我正在为自己和朋友开发一个有趣的小项目,基本上我希望能够使用 ffmpeg 流式传输和接收视频,作为一种屏幕共享应用程序。我是一个彻头彻尾的Python菜鸟,我只是放弃了每个Python的文档。 这是我要发送的内容:
import ffmpeg
stream = ffmpeg.input("video.mp4")
stream = ffmpeg.output(stream, "tcp://127.0.0.1:1234", format="mpegts")
ffmpeg.run(stream)
很简单,但很有效,当我在命令提示符下运行
ffplay.exe -i tcp://127.0.0.1:1234?listen -hide_banner
并运行代码来发送视频时,它工作得很好,但是当我尝试使用我的代码接收视频时,我得到的只是音频,没有视频,视频结束后重复音频的最后一秒。
接收代码如下:
from ffpyplayer.player import MediaPlayer
test = MediaPlayer("tcp://127.0.0.1:1234?listen")
while True:
test.get_frame()
if test == "eof":
break
感谢您的帮助,如果我只是忘记了某些事情,请抱歉:P
您仅在代码中从 video.mp4 中提取帧。
test = MediaPlayer("tcp://127.0.0.1:1234?listen")
while True:
test.get_frame()
if test == "eof":
break
现在,您需要使用一些第三方库来显示它们,因为 ffpyplayer 不提供任何内置功能来循环显示帧。
下面的代码使用 OpenCV 显示提取的帧。使用以下命令安装 OpenCV 和 numpy
pip3 install numpy opencv-python
将您的接收器代码更改为
from ffpyplayer.player import MediaPlayer
import numpy as np
import cv2
player = MediaPlayer("tcp://127.0.0.1:1234?listen")
val = ''
while val != 'eof':
frame, val = player.get_frame()
if val != 'eof' and frame is not None:
img, t = frame
w = img.get_size()[0]
h = img.get_size()[1]
arr = np.uint8(np.asarray(list(img.to_bytearray()[0])).reshape(h,w,3)) # h - height of frame, w - width of frame, 3 - number of channels in frame
cv2.imshow('test', arr)
if cv2.waitKey(25) & 0xFF == ord('q'):
cv2.destroyAllWindows()
break
你也可以直接使用python运行ffplay命令subprocess
借助 Vencat 的 answer,我最初的视频播放有些滞后或“口吃”。经过轻微修改,视频播放就像我在终端上使用
ffplay
运行一样流畅。
将
list()
替换为 []
:
from ffpyplayer.player import MediaPlayer
import numpy as np
import cv2
player = MediaPlayer("udp://127.0.0.1:51234")
val = ''
while val != 'eof':
frame, val = player.get_frame()
if val != 'eof' and frame is not None:
img, t = frame
w = img.get_size()[0]
h = img.get_size()[1]
arr = np.uint8(np.asarray([img.to_bytearray()[0]]).reshape(h,w,3)) # h - height of frame, w - width of frame, 3 - number of channels in frame
arr = cv2.cvtColor(arr, cv2.COLOR_BGR2RGB)
cv2.imshow('test', arr)
if cv2.waitKey(25) & 0xFF == ord('q'):
cv2.destroyAllWindows()
break
使用
np.array
代替Python列表:
from ffpyplayer.player import MediaPlayer
import numpy as np
import cv2
player = MediaPlayer("udp://127.0.0.1:51234")
val = ''
while val != 'eof':
frame, val = player.get_frame()
if val != 'eof' and frame is not None:
img, t = frame
w = img.get_size()[0]
h = img.get_size()[1]
arr = np.uint8(np.array(img.to_bytearray()[0]).reshape(h,w,3)) # h - height of frame, w - width of frame, 3 - number of channels in frame
arr = cv2.cvtColor(arr, cv2.COLOR_BGR2RGB)
cv2.imshow('test', arr)
if cv2.waitKey(25) & 0xFF == ord('q'):
cv2.destroyAllWindows()
break