How to draw a polyline on video frames using opencv?
Mia Lopez
I have a x and y co ordinates of 50 frames in a video. i am trying to draw a polyline for these frames. instead of drawing a line for these co ordinates, i am just getting a single dot in one fixed place like this.(or am i using wrong thing(polyline) to solve this problem?)
desired output:
points is my numpy array having x,y co ordinates for these 50 frames:
[[400 341] [401 345] [400 344] [400 340] [401 344].........]here is my code for drawing polyline:
idx =0
#capture video
vs = cv2.VideoCapture(video_path)
#initialsing tracker
tracker= cv2.TrackerCSRT_create
#loop over frames
while True:
# grab the current frame,
frame = vs.read()
# check to see if we have reached the end of the stream
if frame is None: break
# frame dimensions
(H, W) = frame.shape[:2] this is the part for drawing, rest of the code i didnt include is just about initialising the object tracking algorithm
# check to see if the tracking was a success if success: (x, y, w, h) = [int(v) for v in box] cv2.rectangle(frame, (x, y), (x + w, y + h), (0, 255, 0), 2) cv2.line(frame, (x + w // 2, y), (x + w // 2, y + h), (0, 0,255), 2) center = (x + w // 2, y + h // 2) radius = 2 cv2.circle(frame, center, radius, (255, 255, 0), 2) #if frame number is in in range (600-650) draw polyline with the co ordinates stored in points if idx in range(600, 650): cv2.polylines(frame, np.int32([points]), isClosed=True, color=(0,0, 255), thickness=2)
idx=idx+1Can someone tell me how to do it?
171 Answer
The image you posted recently is a lot clearer.
Based on this snippet:
[[400 341] [401 345] [400 344] [400 340] [401 344].........]the assumption is the 50 points you want to draw are numpy int32 array with shape (50, 2) stored as the variable named points.
If so, you want to reshape it as mentioned above and use the False argument in polylines() to draw the line path (instead of a closed polygon):
cv2.polylines(frame, [points], isClosed=False, color=(0,0, 255), thickness=2)(We're using [points] instead of points because points are the data for a single poly line while cv2.polylines() can draw multiple poly lines (e.g. cv.polylines(frame, [points1, points2, ...], etc.))
Update
Based on your comment I see all the points are moving in a very narrow regions. While the cv2.polyline drawing may work because of your values it will look a tiny blob when you're expecting a large path. The poly line drawing use though.
Here's a demo of your data with two poly lines drawn: in green is your original data, in red is your data offset to the top left corner and scaled up by a factor of 60:
import cv2
import numpy as np
points = np.array([[400, 341], [401, 345], [400, 344], [400, 340], [401, 344], [401, 346], [401, 344], [402, 345], [398, 346], [399, 345], [400, 343], [399, 343], [399, 344], [399, 344], [402, 345], [398, 343], [399, 344], [400, 342], [398, 342], [399, 343], [400, 342], [399, 343], [402, 344], [398, 344], [399, 343], [400, 343], [400, 343], [401, 342], [401, 343], [401, 343], [398, 343], [399, 342], [400, 341], [399, 342], [400, 342], [399, 341], [399, 341], [400, 341], [399, 342], [402, 341], [398, 341], [399, 342], [401, 343], [401, 342], [401, 342], [398, 342], [399, 344], [400, 342], [399, 345], [397, 342]], dtype=np.int32)
# use this blank image as a placeholder for your camera image
frame = np.zeros((480, 640, 3), dtype=np.uint8)
# draw original polylines
cv2.polylines(frame, [points], isClosed=False, color=(0, 192, 0), thickness=1)
cv2.putText(frame,"original data", tuple(points.min(axis = 0) + [3, -6]), 0, 0.75, (255, 255, 255))
# quick'n'dirty offset and scale points (60 times !!!) for visualisation purposes
cv2.polylines(frame, [((points - points.min(axis = 0)) * 60)], isClosed=False, color=(0, 0, 192), thickness=2)
cv2.putText(frame,"scaled data", (9, 21), 0, 0.75, (255, 255, 255))
# preview
cv2.imshow('polylines debug demo', frame)Feel free to tinker with the data in this colab notebook
Now why the tracked points are a small blob is a different problem / question altogether related potentially to the data and how tracking is done: a great candidate for another post perhaps.