通过python的opencv获取rtsp视频流,然后websocket实时发送base64图片到前端html显示。缺点无法播放声音。
1.安装opencv库
pip install opencv-python
2.安装websocket_server库
pip install websocket_server
websocket_server库使python作为websocket服务端,向客户端发送数据。
3.websocket_server使用
# Server Port
PORT=8124
# 创建Websocket Server
server = WebsocketServer(PORT,'127.0.0.1')
from_vedio()
# 有设备连接上了
server.set_fn_new_client(new_client)
# 断开连接
server.set_fn_client_left(client_left)
# 接收到信息
server.set_fn_message_received(message_received)
# 开始监听
server.run_forever()
4.opencv读取视频
在这里用了一个线程实时获取视频并复制到frame
def vedio_thread2(n):
global camera1
camera1 = cv2.VideoCapture(rtsp_path)
global frame
while True:
_, img_bgr = camera1.read()
if img_bgr is None:
camera1 = cv2.VideoCapture(rtsp_path)
print('丢失帧')
else:
frame=img_bgr
5.websocket实时发送到前端HTML显示
这里把图片转换成base64发送
def vedio_thread1(n):
print('send')
while True:
if len(server.clients)>0:
image = cv2.imencode('.jpg', frame)[1]
base64_data = base64.b64encode(image)
s = base64_data.decode()
#print('data:image/jpeg;base64,%s'%s)
server.send_message_to_all('data:image/jpeg;base64,%s'%s)
time.sleep(0.05)
6.HTML显示画面
这里把websocket接受到的base64数据赋值给img的src达到类似视频画面显示
var ws;
var pyip='127.0.0.1';
function startWS() {
console.log('start once again');
ws = new WebSocket("ws://"+pyip+":8124");
ws.onopen = function (msg) {
console.log('webSocket opened');
};
ws.onmessage = function (message) {
//console.log('receive message : ' + message.data);
$("#img").attr("src",message.data);
//var image = new Image();
//image.onload = function () {
// context.clearRect(0, 0, canvas.width, canvas.height);
// context.drawImage(image, 0, 0,canvas.width, canvas.height);
//}
//image.src =message.data;
};
ws.onerror = function (error) {
console.log('error :' + error.name + error.number);
};
ws.onclose = function () {
console.log('webSocket closed');
};
// ws.send("websocket from js");
}
startWS();
后端代码
from websocket_server import WebsocketServer
import threading
import cv2
import base64
import time
camera1=None
frame=cv2.imread("1.jpg", cv2.IMREAD_COLOR)
rtsp_path=0
# Called for every client connecting (after handshake)
def new_client(client, server):
print("New client connected and was given id %d" % client['id'])
# 发送给所有的连接
server.send_message_to_all("Hey all, a new client has joined us")
# Called for every client disconnecting
def client_left(client, server):
print("Client(%d) disconnected" % client['id'])
# Called when a client sends a message
def message_received(client, server, message):
if len(message) > 200:
message = message[:200]+'..'
print("Client(%d) said: %s" % (client['id'], message))
global camera1
camera1 = cv2.VideoCapture(message)
# 发送给所有的连接
#server.send_message_to_all(message)
def from_vedio():
thread1 = threading.Thread(target=vedio_thread1, args=(1,))
# thread1.setDaemon(True)
thread1.start()
thread2 = threading.Thread(target=vedio_thread2, args=(1,))
# thread1.setDaemon(True)
thread2.start()
print('start')
def vedio_thread1(n):
print('send')
while True:
if len(server.clients)>0:
image = cv2.imencode('.jpg', frame)[1]
base64_data = base64.b64encode(image)
s = base64_data.decode()
#print('data:image/jpeg;base64,%s'%s)
server.send_message_to_all('data:image/jpeg;base64,%s'%s)
time.sleep(0.05)
def vedio_thread2(n):
global camera1
camera1 = cv2.VideoCapture(rtsp_path)
global frame
while True:
_, img_bgr = camera1.read()
if img_bgr is None:
camera1 = cv2.VideoCapture(rtsp_path)
print('丢失帧')
else:
frame=img_bgr
# Server Port
PORT=8124
# 创建Websocket Server
server = WebsocketServer(PORT,'127.0.0.1')
from_vedio()
# 有设备连接上了
server.set_fn_new_client(new_client)
# 断开连接
server.set_fn_client_left(client_left)
# 接收到信息
server.set_fn_message_received(message_received)
# 开始监听
server.run_forever()
此方法能简单实现html播放rtsp