Object Tracking on a video using bbox, opencv and python - python

I am trying to create an robot that can follow a human that I chose, for that I am usig raspberry pi with python and openCV.
I want to create bbox around a human, and I want my camera to track that human, I found pieces of codes on internet and I tried to put them together but when I start the code it gives me image, I can select an object but it doesn't update the frames and the image is freezed.
It also gives me an error when ii press space or another key:
"ok = tracker.init(image, bbox)
NameError: name 'tracker' is not defined"
Can someone give me some advices?
Here is the code only for object tracking:
from picamera import PiCamera
import time
import cv2
import numpy as np
# initialize the camera and grab a reference to the raw camera capture
camera = PiCamera()
camera.resolution = (640, 480)
camera.framerate = 32
rawCapture = PiRGBArray(camera, size=(640, 480))
while True:
for frame in camera.capture_continuous(rawCapture, format="bgr", use_video_port=True):
image = frame.array
bbox = cv2.selectROI(image, False)
ok = tracker.init(image, bbox)
cv2.imshow("Camera Output", image)
#rawCapture.truncate(0)
ok, bbox = tracker.update(image)
fps = cv2.getTickFrequency() / (cv2.getTickCount() - timer)
if ok:
p1 = (int(bbox[0]), int(bbox[1]))
p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
cv2.rectangle(frame, pi, p2, (255, 0, 0), 2, 1)
else:
cv2.putText(image, "Tracking failure detected", (100, 80),
cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)
cv2.putText(frame, tracker_type + "Tracker", (100, 20),
cv2.FONT_HERSHEY_SIMPLEX, 0.75, (50, 170, 50), 2);
cv2.putText(image, "FPS:" ++ str(int(fps)), (100, 50),
cv2.FONT_HERSHEY_SIMPLEX, 0.75, (50, 170, 50), 2);
cv2.imshow("Tracking", image)
k = cv2.waitKey(5) #& 0xFF
if "q" == chr(k & 255):
break```

So the method tracker is not defined. I found this which initializes the method. YOu can do it like this:
tracker = cv2.TrackerKCF_create()
This is considering that you want to implement opencv function

Related

I am not understanding the reason for this error 'cameraMatrix' is an invalid keyword argument for detectMarkers()

Full error is:
OpenCV(4.7.0) :-1: error: (-5:Bad argument) in function 'detectMarkers'
> Overload resolution failed:
> - 'cameraMatrix' is an invalid keyword argument for detectMarkers()
My camera calibration code works fine (to my understanding) i have input my values however when i run the code i am still getting cameraMatrix errors. Please help me understand why i would be getting this error.
import numpy as np
import cv2
import sys
import time
ARUCO_DICT = {
"DICT_4X4_50": cv2.aruco.DICT_4X4_50,
"DICT_4X4_100": cv2.aruco.DICT_4X4_100,
"DICT_4X4_250": cv2.aruco.DICT_4X4_250,
"DICT_4X4_1000": cv2.aruco.DICT_4X4_1000,
"DICT_5X5_50": cv2.aruco.DICT_5X5_50,
"DICT_5X5_100": cv2.aruco.DICT_5X5_100,
"DICT_5X5_250": cv2.aruco.DICT_5X5_250,
"DICT_5X5_1000": cv2.aruco.DICT_5X5_1000,
"DICT_6X6_50": cv2.aruco.DICT_6X6_50,
"DICT_6X6_100": cv2.aruco.DICT_6X6_100,
"DICT_6X6_250": cv2.aruco.DICT_6X6_250,
"DICT_6X6_1000": cv2.aruco.DICT_6X6_1000,
"DICT_7X7_50": cv2.aruco.DICT_7X7_50,
"DICT_7X7_100": cv2.aruco.DICT_7X7_100,
"DICT_7X7_250": cv2.aruco.DICT_7X7_250,
"DICT_7X7_1000": cv2.aruco.DICT_7X7_1000,
"DICT_ARUCO_ORIGINAL": cv2.aruco.DICT_ARUCO_ORIGINAL,
"DICT_APRILTAG_16h5": cv2.aruco.DICT_APRILTAG_16h5,
"DICT_APRILTAG_25h9": cv2.aruco.DICT_APRILTAG_25h9,
"DICT_APRILTAG_36h10": cv2.aruco.DICT_APRILTAG_36h10,
"DICT_APRILTAG_36h11": cv2.aruco.DICT_APRILTAG_36h11
}
def aruco_display(corners, ids, rejected, image):
if len(corners) > 0:
ids = ids.flatten()
for (markerCorner, markerID) in zip(corners, ids):
corners = markerCorner.reshape((4, 2))
(topLeft, topRight, bottomRight, bottomLeft) = corners
topRight = (int(topRight[0]), int(topRight[1]))
bottomRight = (int(bottomRight[0]), int(bottomRight[1]))
bottomLeft = (int(bottomLeft[0]), int(bottomLeft[1]))
topLeft = (int(topLeft[0]), int(topLeft[1]))
cv2.line(image, topLeft, topRight, (0, 255, 0), 2)
cv2.line(image, topRight, bottomRight, (0, 255, 0), 2)
cv2.line(image, bottomRight, bottomLeft, (0, 255, 0), 2)
cv2.line(image, bottomLeft, topLeft, (0, 255, 0), 2)
cX = int((topLeft[0] + bottomRight[0]) / 2.0)
cY = int((topLeft[1] + bottomRight[1]) / 2.0)
cv2.circle(image, (cX, cY), 4, (0, 0, 255), -1)
cv2.putText(image, str(markerID),(topLeft[0], topLeft[1] - 10), cv2.FONT_HERSHEY_SIMPLEX,
0.5, (0, 255, 0), 2)
print("[Inference] ArUco marker ID: {}".format(markerID))
return image
def pose_estimation(frame, aruco_dict_type, matrix_coefficients, distortion_coefficients):
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
cv2.aruco_dict = cv2.aruco.getPredefinedDictionary(aruco_dict_type)
parameters = cv2.aruco.DetectorParameters()
corners, ids, rejected_img_points = cv2.aruco.detectMarkers(gray, cv2.aruco_dict,parameters=parameters,
cameraMatrix=matrix_coefficients,
distCoeff=distortion_coefficients)
if len(corners) > 0:
for i in range(0, len(ids)):
rvec, tvec, markerPoints = cv2.aruco.estimatePoseSingleMarkers(corners[i], 0.02, matrix_coefficients,
distortion_coefficients)
cv2.aruco.drawDetectedMarkers(frame, corners)
cv2.aruco.drawAxis(frame, matrix_coefficients, distortion_coefficients, rvec, tvec, 0.01)
return frame
aruco_type = "DICT_4X4_50"
arucoDict = cv2.aruco.getPredefinedDictionary(ARUCO_DICT[aruco_type])
arucoParams = cv2.aruco.DetectorParameters()
intrinsic_camera = np.array(((981.69820777, 0, 637.86160616),(0,983.8672381, 364.31555519),(0,0,1)))
distortion = np.array((0.0366562741,-0.153342145,-0.000307462615,-0.000078917106,0.215865749))
cap = cv2.VideoCapture(0)
cap.set(cv2.CAP_PROP_FRAME_WIDTH, 1280)
cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 720)
while cap.isOpened():
ret, img = cap.read()
output = pose_estimation(img, ARUCO_DICT[aruco_type], intrinsic_camera, distortion)
cv2.imshow('Estimated Pose', output)
key = cv2.waitKey(1) & 0xFF
if key == ord('q'):
break
cap.release()
cv2.destroyAllWindows()
I just want to understand why this error is popping up so i can move on :D
OpenCV's aruco API changed in the past year or so, after v4.5.5.
Some APIs that should not deal with intrinsics did previously accept intrinsics parameters. Not any longer.
Detection (detectMarkers()) is a purely 2D operation that should never deal with intrinsics. It returns screen-space 2D coordinates for the corners of each marker.
Pose estimation (estimatePoseSingleMarkers()) should take intrinsics.
It was always an error to pass intrinsics to both APIs at the same time.

cv2.findcontours returning none in Motion Detector App

I followed a video online about motion detection using openCV however I came across the problem that the findContours function is not returning a value. Any help is appreceated.
Here is the code:
import cv2
import time
import datetime
import imutils
def motion_detection():
video_capture = cv2.VideoCapture(0, cv2.CAP_DSHOW)
time.sleep(2)
first_frame = None
while True:
frame = video_capture.read()[1]
text = 'Unoccupied'
greyscale_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
gaussian_frame = cv2.GaussianBlur(greyscale_frame, (21, 21), 0)
blur_frame = cv2.blur(gaussian_frame, (5, 5))
greyscale_image = blur_frame
if first_frame is None:
first_frame = greyscale_image
else:
pass
frame = imutils.resize(frame, width=500)
frame_delta = cv2.absdiff(first_frame, greyscale_image)
# edit the ** thresh ** depending on the light/dark in room,
# change the 100(anything pixel value over 100 will become 255(white)
thresh = cv2.threshold(frame_delta, 100, 255, cv2.THRESH_BINARY)[1]
dilate_image = cv2.dilate(thresh, None, iterations=2)
cnt = cv2.findContours(dilate_image.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)[1]
for c in cnt:
if cv2.contourArea(c) > 800:
(x, y, w, h) = cv2.boundingRect(
c)
cv2.rectangle(frame, (x, y), (x + w, y + h), (0, 255, 0), 2)
text = 'Occupied'
# text that appears when there is motion in video feed
else:
pass
''' now draw text and timestamp on security feed '''
font = cv2.FONT_HERSHEY_SIMPLEX
cv2.putText(frame, '{+} Room Status: %s' % text, (10, 20), cv2.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 255), 2)
cv2.putText(frame, datetime.datetime.now().strftime('%A %d %B %Y %I:%M:%S%p'),
(10, frame.shape[0] - 10), font, 0.35, (0, 0, 255), 1)
cv2.imshow('Security Feed', frame)
cv2.imshow('Threshold(foreground mask)', dilate_image)
cv2.imshow('Frame_delta', frame_delta)
key = cv2.waitKey(1) & 0xFF
if key == ord('q'):
cv2.destroyAllWindows()
break
if __name__ == '__main__':
motion_detection()
I have tried to debug and find the problem the code is exactly what the video said to write and I have had no luck.

cv2.waitKey() works for 'q' key but does not works for any other keys

I have this code which is actually a part of one of my projects for Sign Language Recognition.
So I am taking user's hand image in each frame and passing it to model and showing the prediction for the sign on the screen and I have added a feature where if user presses 's' key then prediction will get appended to string sen and similarily I will show that string sen on screen .
But after running the code, for key 'q' it closes the window without any problems but when I press key 's' nothing happens.
Instead of key 's' , I tried the same with other keys but still nothing happens.
Here's the code :
import cv2
import numpy as np
from model import predict
def capture():
sen = ''
cap = cv2.VideoCapture(0)
while True:
ret, frame = cap.read()
frame = cv2.flip(frame, 1)
frame_height = 480
frame_width = 640
# a standard frame window of size 640*480
frame = cv2.resize(frame, (frame_width, frame_height))
# drawing a rectangle in a frame which will capture hand
cv2.rectangle(frame, (300, 100), (500, 300), (0, 300, 0), 2)
# rectangle of background of text s
cv2.rectangle(frame, (0, 0), (300, 50), (0, 0, 0), -1)
frame = cv2.putText(frame, 'press q to exit', (30, 30), cv2.FONT_HERSHEY_SIMPLEX,
1, (255, 255, 255), 1, cv2.LINE_AA)
# region of interest i.e rectangle which we drawn earlier
roi = frame[100:300, 300:500]
roi = cv2.cvtColor(roi, cv2.COLOR_BGR2GRAY)
roi = cv2.GaussianBlur(roi, (5, 5), 0)
# applying edge detection on roi
roi_edges = cv2.Canny(roi, 100, 200)
# cv2.imshow('Edges', roi_edges)
# to make roid_edges of shape (200,200,1) , specifying color channel which is required for model
img = np.expand_dims(roi_edges, axis=2)
cv2.imshow('input for model', img)
frame = cv2.putText(frame, predict(img), (300, 400), cv2.FONT_HERSHEY_SIMPLEX,
1, (255, 255, 255), 1, cv2.LINE_AA)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
elif cv2.waitKey(1) & 0xFF == ord('s'):
sen += predict(img)
print(sen)
# printing whole sentence i.e. sen
frame = cv2.putText(frame, sen , (300, 500),
cv2.FONT_HERSHEY_SIMPLEX, 1, (255, 255, 255), 1, cv2.LINE_AA)
cv2.imshow('Smile', frame)
cv2.destroyAllWindows()
cap.release()
capture()
So what could be the problem here?
The problem is you called the cv2.waitKey(1) method multiple times, in this case you should use variable for cv2.waitKey(1) because the waiting is that both function calls read the keyboard buffer so the second branch executed only if the software receives the s key right after the evaulation of the first branch (q). Here is the sample code:
keys = cv2.waitKey(1) & 0xFF
if keys == ord('q'):
break
elif keys == ord('s'):
print('s is pressed')

OpenCV video writing decreases FPS drastically. How to optimize performance?

I'm working on a project that involves object detection + sort tracking.
I have scripts to work with videos an camera using OpenCV in the Coral dev board.
The main issue is when make usage of the VideoWriter to save the output of the detections.
For camera script it's usage decreases fps rate from 11 to 2.3 and for video script from 6-7 to 2.
Is there a way to solve/optimize this issue.
Here is my portion of code that grabs frames, detects and tracks, and then writes.
# Read frames
while(video.isOpened()):
# Acquire frame and resize to expected shape [1xHxWx3]
ret, frame = video.read()
if not ret:
break
# Debug info
frame_count += 1
print("[INFO] Processing frame: {}".format(frame_count))
if FLIP:
frame = cv2.flip(frame, 1)
if ROTATE != 0:
frame = cv2.rotate(frame, ROTATE) # Rotate image on given angle
frame_rgb = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB) # Convert to RGB
frame = cv2.resize(frame, (VIDEO_WIDTH, VIDEO_HEIGHT)) # resize frame to output dims
frame_resized = cv2.resize(frame_rgb, (width, height)) # resize to fit tf model dims
input_data = np.expand_dims(frame_resized, axis=0)
# Normalize pixel values if using a floating model (i.e. if model is non-quantized)
if floating_model:
input_data = (np.float32(input_data) - input_mean) / input_std
# Initialize writer
if (writer is None) and (SAVE_VIDEO) :
writer = cv2.VideoWriter(VIDEO_OUTPUT, cv2.VideoWriter_fourcc(*'XVID'), args.fps, (VIDEO_WIDTH, VIDEO_HEIGHT))
# Perform the actual detection by running the model with the image as input
#s_detection_time = time.time()
interpreter.set_tensor(input_details[0]['index'],input_data)
interpreter.invoke()
#e_detection_time = time.time()
#print("[INFO] Detection time took: {} seconds".format(e_detection_time-s_detection_time))
# Retrieve detection results
boxes = interpreter.get_tensor(output_details[0]['index'])[0] # Bounding box coordinates of detected objects
classes = interpreter.get_tensor(output_details[1]['index'])[0] # Class index of detected objects
scores = interpreter.get_tensor(output_details[2]['index'])[0] # Confidence of detected objects
#num = interpreter.get_tensor(output_details[3]['index'])[0] # Total number of detected objects (inaccurate and not needed)
#print("[INFO] Boxes: {}".format(boxes))
detections = np.array([[]])
#s_detections_loop = time.time()
# Loop over all detections and draw detection box if confidence is above minimum threshold
for i in range(len(scores)):
if ((scores[i] > min_conf_threshold) and (scores[i] <= 1.0)):
#print("[INFO] Box ", i , ": ", boxes[i])
# Get bounding box coordinates and draw box
# Interpreter can return coordinates that are outside of image dimensions, need to force them to be within image using max() and min()
ymin = int(max(1,(boxes[i][0] * VIDEO_HEIGHT)))
xmin = int(max(1,(boxes[i][1] * VIDEO_WIDTH)))
ymax = int(min(VIDEO_HEIGHT,(boxes[i][2] * VIDEO_HEIGHT)))
xmax = int(min(VIDEO_WIDTH,(boxes[i][3] * VIDEO_WIDTH)))
# Calculate centroid of bounding box
#centroid_x = int((xmin + xmax) / 2)
#centroid_y = int((ymin + ymax) / 2)
# Format detection for sort and append to current detections
detection = np.array([[xmin, ymin, xmax, ymax]])
#f.write("Box {}: {}\n".format(i, detection[:4]))
#print("[INFO] Size of detections: ", detections.size)
if detections.size == 0:
detections = detection
else:
detections = np.append(detections, detection, axis=0)
# Draw a circle indicating centroid
#print("[INFO] Centroid of box ", i, ": ", (centroid_x, centroid_y))
#cv2.circle(frame, (centroid_x, centroid_y), 6, (0, 0, 204), -1)
# Calculate area of rectangle
#obj_height = (ymin + ymax)
#print("[INFO] Object height: ", obj_height)
# Check if centroid passes ROI
# Draw the bounding box
#cv2.rectangle(frame, (xmin,ymin), (xmax,ymax), (0, 0, 255), 4)
#print("[INFO] Object passing ROI")
#print("[INFO] Object height: ", obj_height)
#counter += 1
#print("[INFO] Object out of ROI")
# Draw the bounding box
#cv2.rectangle(frame, (xmin,ymin), (xmax,ymax), (10, 255, 0), 4)
#print("[INFO] Total objects counted: ", counter)
# Draw label
"""object_name = labels[int(classes[i])] # Look up object name from "labels" array using class index
label = '%s: %d%%' % (object_name, int(scores[i]*100)) # Example: 'person: 72%'
labelSize, baseLine = cv2.getTextSize(label, cv2.FONT_HERSHEY_SIMPLEX, 0.7, 2) # Get font size
label_ymin = max(ymin, labelSize[1] + 10) # Make sure not to draw label too close to top of window
cv2.rectangle(frame, (xmin, label_ymin-labelSize[1]-10), (xmin+labelSize[0], label_ymin+baseLine-10), (255, 255, 255), cv2.FILLED) # Draw white box to put label text in
cv2.putText(frame, label, (xmin, label_ymin-7), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 0), 2) # Draw label text
"""
#f.write("\n")
#e_detection_loop = time.time()
#print("[INFO] Detection loop time took {} seconds".format(e_detection_loop-s_detections_loop))
#s_tracker_update = time.time()
# Update sort tracker
print("[INFO] Current Detections: ", detections.astype(int))
objects_tracked = tracker.update(detections.astype(int))
#e_tracker_update = time.time()
#print("[INFO] Updating trackers state took {} seconds".format(e_tracker_update-s_tracker_update))
#s_draw_tracked = time.time()
# Process every tracked object
for object_tracked in objects_tracked:
if object_tracked.active:
bbox_color = (0, 128, 255)
else:
bbox_color = (10, 255, 0)
bbox = object_tracked.get_state().astype(int)
# Draw the bbox rectangle
cv2.rectangle(frame, (int(bbox[0]), int(bbox[1])), (int(bbox[2]), int(bbox[3])), bbox_color, 4)
# Calculate centroid of bounding box
centroid = (object_tracked.last_centroid[0], object_tracked.last_centroid[1])
# Draw the centroid
cv2.circle(frame, centroid, 6, (0, 0, 204), -1)
label = '{} [{}]'.format(OBJECT_NAME,object_tracked.id) # Example: 'object [1]'
labelSize, baseLine = cv2.getTextSize(label, FONT, 0.7, 2) # Get font size
label_ymin = max(bbox[1], labelSize[1] + 10) # Make sure not to draw label too close to top of window
cv2.rectangle(frame, (bbox[0], label_ymin-labelSize[1]-10), (bbox[0]+labelSize[0], label_ymin+baseLine-10), (255, 255, 255), cv2.FILLED) # Draw white box to put label text in
cv2.putText(frame, label, (bbox[0], label_ymin-7), FONT, 0.7, (0, 0, 0), 2) # Draw label text
#e_draw_tracked = time.time()
#print("[INFO] Drawing tracked objects took {} seconds".format(e_draw_tracked-s_draw_tracked))
# Update fps count
fps.update()
fps.stop()
# Prepare fps display
fps_label = "FPS: {0:.2f}".format(fps.fps())
cv2.rectangle(frame, (0, 0), (int(VIDEO_WIDTH*0.6), int(VIDEO_HEIGHT*0.07)), (255, 255, 255), cv2.FILLED)
cv2.putText(frame, fps_label, (int(VIDEO_WIDTH*0.01), int(VIDEO_HEIGHT*0.05)), FONT, 1.5, (10, 255, 0), 3)
# Prepare total and active objects count display
total_objects_text = "TOTAL {}S: {}".format(OBJECT_NAME,tracker.total_trackers)
active_objects_text = "ACTIVE {}S: {}".format(OBJECT_NAME,tracker.active_trackers)
cv2.putText(frame, total_objects_text, (int(VIDEO_WIDTH*0.1+VIDEO_WIDTH*0.06), int(VIDEO_HEIGHT*0.05)), FONT, 1.5, (0, 0, 255), 3) # Draw label text
cv2.putText(frame, active_objects_text, (int(VIDEO_WIDTH*0.1+VIDEO_WIDTH*0.27), int(VIDEO_HEIGHT*0.05)), FONT, 1.5, (0, 128, 255), 3) # Draw label text
# Draw horizontal boundaries
cv2.line(frame, (LEFT_BOUNDARY, int(VIDEO_HEIGHT*0.07)), (LEFT_BOUNDARY, VIDEO_HEIGHT), (0, 255, 255), 4)
#cv2.line(frame, (RIGHT_BOUNDARY, 0), (RIGHT_BOUNDARY, VIDEO_HEIGHT), (0, 255, 255), 4)
#s_trackers_state = time.time()
tracker.update_trackers_state()
#e_trackers_state = time.time()
#print("[INFO] Updating trackers state took {} seconds".format(e_trackers_state-s_trackers_state))
# All the results have been drawn on the frame, so it's time to display it.
cv2.imshow('Object detector', frame)
# Center window
if not IS_CENTERED:
cv2.moveWindow('Object detector', 0, 0)
IS_CENTERED = True
if SAVE_VIDEO:
writer.write(frame)
print("\n\n")
# Press 'q' to quit
if cv2.waitKey(1) == ord('q'):
break
Thanks in advance for any help!
An important thing when trying to optimize/improve code performance is to categorize and measure your code execution. Only after identifying what is actually causing the bottleneck or performance decrease then can you can work on improving those sections of code. For this approach I'm assuming that you're both reading and saving frames in the same thread. So if you're facing a performance reduction due to I/O latency then this method can help otherwise if you find out that your problem is due to CPU processing limitations then this method will not give you a performance boost.
That being said, the approach is to use threading. The idea is to create another separate thread for obtaining the frames as cv2.VideoCapture.read() is blocking. This can be expensive and cause latency as the main thread has to wait until it has obtained a frame. By putting this operation into a separate thread that just focuses on grabbing frames and processing/saving the frames in the main thread, it dramatically improves performance due to I/O latency reduction. Here's a simple example on how to use threading to read frames in one thread and show/save frames in the main thread. Be sure to change the capture_src to your stream.
Code
from threading import Thread
import cv2
class VideoWritingThreading(object):
def __init__(self, src=0):
# Create a VideoCapture object
self.capture = cv2.VideoCapture(src)
# Default resolutions of the frame are obtained (system dependent)
self.frame_width = int(self.capture.get(3))
self.frame_height = int(self.capture.get(4))
# Set up codec and output video settings
self.codec = cv2.VideoWriter_fourcc('M','J','P','G')
self.output_video = cv2.VideoWriter('output.avi', self.codec, 30, (self.frame_width, self.frame_height))
# Start the thread to read frames from the video stream
self.thread = Thread(target=self.update, args=())
self.thread.daemon = True
self.thread.start()
def update(self):
# Read the next frame from the stream in a different thread
while True:
if self.capture.isOpened():
(self.status, self.frame) = self.capture.read()
def show_frame(self):
# Display frames in main program
if self.status:
cv2.imshow('frame', self.frame)
# Press Q on keyboard to stop recording
key = cv2.waitKey(1)
if key == ord('q'):
self.capture.release()
self.output_video.release()
cv2.destroyAllWindows()
exit(1)
def save_frame(self):
# Save obtained frame into video output file
self.output_video.write(self.frame)
if __name__ == '__main__':
capture_src = 'your stream link!'
video_writing = VideoWritingThreading(capture_src)
while True:
try:
video_writing.show_frame()
video_writing.save_frame()
except AttributeError:
pass

OpenCV.putext: only size-1 arrays problem

In this script below I am experimenting around with OpenCV and calculating a distance to my laptop webcam of a face detection with Haar Cascades. I am using a windows 10 laptop with a web cam, Python 3.6, and OpenCV 3.4.
I am having an issue with the OpenCV.putext of displaying this calculated value on the view of the video stream…
text = "Inches{}".format(np.int(inches))
cv2.putText(gray, text, (roi[0] - 10, roi[1] - 10),
cv2.FONT_HERSHEY_SIMPLEX, 0.6, (255, 255, 255), 2)
The code will run if this is commented out.. Any tips for what I am doing wrong would be greatly appreciated!
import numpy as np
import imutils
import cv2
from imutils.video import VideoStream
from imutils.video import FPS
import time
def distance_to_camera(knownWidth, focalLength, perWidth):
# compute and return the distance from the maker to the camera
return (knownWidth * focalLength) / perWidth
face_cascade = cv2.CascadeClassifier('C:/Users/Haar/frontalFace10/haarcascade_frontalface_alt.xml')
#Calculated from a different script
focalLength = 709.0909090909091
#average human head width
knownWidth = 7
# Initialize mutithreading the video stream.
camera = VideoStream(src=0).start()
# Allow the camera to warm up.
time.sleep(2.0)
#start FPS
fps = FPS().start()
roi = None
while True:
image = camera.read()
image = imutils.resize(image, width=500)
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
faces = face_cascade.detectMultiScale(gray, scaleFactor=1.1, minNeighbors=5);
for (x, y, w, h) in faces:
cv2.rectangle(gray,(x,y),(x+w,y+h),(255,255,255),2)
roi = gray[y:y+h, x:x+w]
if roi is None:
pass
else:
inches = distance_to_camera(knownWidth, focalLength, roi.shape[1])
print(inches)
text = "Inches{:.2f}".format(np.int(inches))
cv2.putText(gray, text, (roi[0] - 10, roi[1] - 10),
cv2.FONT_HERSHEY_SIMPLEX, 0.6, (255, 255, 255), 2)
cv2.imshow("gray", gray)
key = cv2.waitKey(1) & 0xFF
fps.update()
# if the `q` key was pressed, break from the loop
if key == ord("q"):
break
fps.stop()
print("[INFO] elapsed time: {:.2f}".format(fps.elapsed()))
print("[INFO] approx. FPS: {:.2f}".format(fps.fps()))
camera.stop()
cv2.destroyAllWindows()
This is the full traceback of the error:
Traceback (most recent call last):
File "C:\Users\distance-to-camera\selectHaar3.py", line 53, in <module>
cv2.FONT_HERSHEY_SIMPLEX, 0.6, (255, 255, 255), 2)
TypeError: only size-1 arrays can be converted to Python scalars
>>>
roi[0] and roi[1] are arrays.
I think wat you are trying to do is:
cv2.putText(gray, text, (x - 10, y - 10),
cv2.FONT_HERSHEY_SIMPLEX, 0.6, (255, 255, 255), 2)

Categories

Resources