With the current code, I can only send the video frame to the webpage. How can I also send some text along with each frame and have it displayed.
FastAPI code
def generate_frames(cap,i):
while True:
success,frame = cap.read()
if not success:
break
else:
# Reshape image
im_arr = cv2.imencode('.jpg', frame)[1]
cv2.waitKey(50)
print(loa[i]) //text to be displayed along with image
i = i 1
yield (b'--frame\r\n'
b'Content-Type: image/jpeg\r\n\r\n' bytearray(im_arr) b'\r\n')
@app.get('/video')
def video():
i = 0
cap = cv2.VideoCapture('C:\\Users\\ryanv_k78mbsh\\Desktop\\FINAL\\MovenetTest\\animation.gif')
return StreamingResponse(generate_frames(cap,i),media_type = 'multipart/x-mixed-replace; boundary=frame')
HTML code that receives and displays the video frame
<div style= "height:50px"></div>
<img src ="{{ url_for('video') }}" width="50%" />
</div>
CodePudding user response:
You could use WebSockets
instead, as described in this answer (Option 2), and send both the text and image bytes to the frontend. Example below:
app.py
from fastapi import FastAPI, Request, WebSocket, WebSocketDisconnect
from fastapi.templating import Jinja2Templates
import uvicorn
import cv2
app = FastAPI()
camera = cv2.VideoCapture(0,cv2.CAP_DSHOW)
templates = Jinja2Templates(directory="templates")
@app.get('/')
def index(request: Request):
return templates.TemplateResponse("index.html", {"request": request})
@app.websocket("/ws")
async def get_stream(websocket: WebSocket):
await websocket.accept()
try:
while True:
success, frame = camera.read()
if not success:
break
else:
ret, buffer = cv2.imencode('.png', frame)
await websocket.send_text("some text")
await websocket.send_bytes(buffer.tobytes())
except WebSocketDisconnect:
print("Client disconnected")
if __name__ == '__main__':
uvicorn.run(app, host='127.0.0.1', port=8000)
templates/index.html
<!DOCTYPE html>
<html>
<head>
<title>Live Streaming</title>
</head>
<body>
<img id="frame" src="">
<div id="textArea"></div>
<script>
let ws = new WebSocket("ws://localhost:8000/ws");
ws.onmessage = function(event) {
if (typeof event.data === 'string')
document.getElementById("textArea").innerHTML = event.data;
else{
let blob = new Blob([event.data])
let blobURL = URL.createObjectURL(blob);
let image = document.getElementById("frame");
image.src = blobURL;
}
};
</script>
</body>
</html>