Navigating the Future with Dynamic Face Detection
Welcome to the forefront of dynamic vision! In this guide, we’ll embark on a captivating journey into the realm of precision face tracking using OpenCV with Python and pan/tilt servos. Imagine the possibilities as your projects gain the ability to autonomously follow and engage with faces in real-time. From the intricacies of face detection to the dynamic control of servos, this tutorial is your gateway to creating responsive, intelligent systems. Let’s delve into the art of guiding vision with unparalleled accuracy and finesse.
What’s Covered:
- The Face Tracking Program.
- Breaking Down the Code.
The Face Tracking Program
We are going to jump straight into this, below is the full code for the program. Open a new file in Visual Studio then copy and paste the code below:
Python Code:
from adafruit_servokit import ServoKit import cv2 import time width=640 height=480 kit=ServoKit(channels=16) pan=0 tilt=135 #Servo [0]=Left & Right #Servo [1]=Up & Down kit.servo[0].angle=pan kit.servo[1].angle=tilt camera=cv2.VideoCapture(0) camera.set(cv2.CAP_PROP_FRAME_WIDTH,width) camera.set(cv2.CAP_PROP_FRAME_HEIGHT,height) face_cascade=cv2.CascadeClassifier('/home/meganano/Desktop/Python-AI/haarcascades/haarcascade_frontalface_default.xml') while True: ret, frame=camera.read() gray=cv2.cvtColor(frame,cv2.COLOR_BGR2GRAY) faces=face_cascade.detectMultiScale(gray,1.3,5) #Tracking for (x,y,w,h) in faces: #Put Box Around Face cv2.rectangle(frame,(x,y),(x+w,y+h),(100,255,100),2) Xcent=x+w/2 Ycent=y+h/2 errorPan=Xcent-width/2 errorTilt=Ycent-height/2 if abs(errorPan)>15: pan=pan-errorPan/30 if abs(errorTilt)>15: tilt=tilt+errorTilt/30 #Print Servo Positions print(pan) print(tilt) #Pan Range Limit if pan>180: pan=180 print('Pan out of range') if pan<0: pan=0 print('Pan out of range') #Tilt Range Limit if tilt>180: tilt=180 print('Tilt out of range') if tilt<0: tilt=0 print('Tilt out of range') kit.servo[0].angle=pan kit.servo[1].angle=tilt roi_gray=gray[y:y+h, x:x+w] roi_color=frame[y:y+h, x:x+w] #Show Frame cv2.imshow('Face Tracker',frame) cv2.moveWindow('Face Tracker',0,0) if cv2.waitKey(1)==ord('q'): break camera.release() cv2.destroyAllWindows() #Reset Camera Position kit.servo[0].angle=0 kit.servo[1].angle=135 print('Program Terminated')
Breaking Down the Code
Import the Libraries
from adafruit_servokit import ServoKit import cv2 import time
Create the ServoKit
Object.
kit=ServoKit(channels=16)
Create Pan
and Tilt
Objects and Apply Them to the ServoKit
Object.
pan=0 tilt=135 kit.servo[0].angle=pan kit.servo[1].angle=tilt
Load the Face Cascade Classifier:
OpenCV provides pre-trained cascade classifiers for detecting faces. You can download the XML file for the face cascade classifier from the OpenCV GitHub repository. Once downloaded, load the classifier using the cv2.CascadeClassifier
function.
face_cascade = cv2.CascadeClassifier('path_to_xml_file/haarcascade_frontalface_default.xml')
Initialize the Video Capture:
Use the cv2.VideoCapture
function to initialize the video capture. You can pass the argument 0
to capture video from the default camera or specify the path to a video file.
cap = cv2.VideoCapture(0)
Read and Process Frames:
Continuously read frames from the video capture and process them for face tracking. Convert the frames to grayscale for better face detection performance.
while True: ret, frame = cap.read() if not ret: break gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
Detect Faces in the Frame:
Use the detectMultiScale
function of the face cascade classifier to detect faces in the grayscale frame.
faces = face_cascade.detectMultiScale(gray, scaleFactor=1.1, minNeighbors=5, minSize=(30, 30))
Adding Bounding Box to Faces:
Iterate over the detected faces and draw rectangles around them on the frame.
for (x, y, w, h) in faces: cv2.rectangle(frame, (x, y), (x + w, y + h), (0, 255, 0), 2)
Track the Faces:
Create conditions using mathematical operations to calculate the Pan and Tilt servo positions.
Xcent=x+w/2 Ycent=y+h/2 errorPan=Xcent-width/2 errorTilt=Ycent-height/2 if abs(errorPan)>15: pan=pan-errorPan/30 if abs(errorTilt)>15: tilt=tilt+errorTilt/30
Add Error Correction:
By adding range limitations, we can fix out of range errors.
if pan>180: pan=180 print('Pan out of range') if pan<0: pan=0 print('Pan out of range') if tilt>180: tilt=180 print('Tilt out of range') if tilt<0: tilt=0 print('Tilt out of range')
Control servo positions:
By applying the updated Pan and Tilt positions each time through the loop.
kit.servo[0].angle=pan kit.servo[1].angle=tilt roi_gray=gray[y:y+h, x:x+w] roi_color=frame[y:y+h, x:x+w]
Display the Frame:
Show the processed frame with the tracked faces using the cv2.imshow
function.
cv2.imshow('Face Tracking', frame)
Exit the Program:
Add a condition to exit the loop and release the video capture when a specific key (e.g., ‘q’) is pressed.
if cv2.waitKey(1) == ord('q'): break cap.release() cv2.destroyAllWindows()
Conclusion
Congratulations, visionary! You’ve successfully navigated the intricacies of tracking faces with pan/tilt servos using OpenCV. By mastering the art of dynamic face detection, you’ve opened the door to a world of interactive, intelligent projects. As you reflect on the journey, remember that this is just the beginning. The skills you’ve acquired here will serve as a solid foundation for more advanced computer vision endeavors.
Stay tuned for upcoming posts where we’ll continue to explore the frontiers of dynamic vision. From object recognition to color tracking, the possibilities are endless. Your projects are now equipped to engage with the world in a whole new way.
In the next installment of our OpenCV for Beginners guide we will be Detecting and Tracking Colors
That’s All Folks!
You can find all of our OpenCV guides here: OpenCV for Beginners