Created
October 17, 2020 13:21
-
-
Save RamiAwar/ba4b55b1488523315c6ca6974051fcab to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
'''This python code performs face tracking and simulates scrolling. First, the image feed is recieved from the camera. A facial detection algorithm is applied | |
once in every 5 frames. On detecting the face, a rectangular frame is drawn around the detected face, and the deviation from the center of the screen to the center of the face is taken as the scroll delta. | |
Requires Python + OpenCV''' | |
import cv2 | |
from pynput.mouse import Button, Controller | |
mouse = Controller() | |
HAAR_CASCADE_PATH = "haarcascade_frontalface_alt.xml" | |
CAMERA_INDEX = 0 | |
def detect_faces(image): | |
# print('detect fn' #) | |
faces = [] | |
# detected = cv.HaarDetectObjects(image, cascade, storage, 1.2, 2, | |
# cv.CV_HAAR_DO_CANNY_PRUNING, (100,100)) | |
detected = cascade.detectMultiScale( | |
image, 1.3, 4, cv2.CASCADE_SCALE_IMAGE, (20, 20)) | |
# print(detected) | |
if detected != []: | |
# print('face detected' #) | |
for (x, y, w, h) in detected: # for (x,y,w,h),n in detected: | |
faces.append((x, y, w, h)) | |
return faces | |
def get_motion(face): | |
# yaw is x-axis - horizontal axis | |
# pitch is y-axis - depth axis | |
# roll is z-axis - vertical axis | |
#[0][0] - x, [0][1] - y, [0][2] - w, [0][3] - h | |
threshold = 40 | |
# w,h are approx constant for U,D,L,R events | |
# checking if w,h in range of origin(w,h)+/-5 | |
if (face[0][2] > (origin[0][2] - threshold)) and (face[0][2] < (origin[0][2] + threshold)) and (face[0][3] > (origin[0][3] - threshold)) and (face[0][3] < (origin[0][3] + threshold)): | |
# check x while y is same | |
if face[0][1] > (origin[0][1] - threshold) and face[0][1] < (origin[0][1] + threshold): | |
if face[0][0] > (origin[0][0] - threshold) and face[0][0] < (origin[0][0] + threshold): | |
# user is in origin location | |
print('origin') | |
return 25 # no motion | |
else: | |
if (face[0][0] - origin[0][0]) > 0: | |
# LEFT motion event - S button | |
print('LEFT') | |
return 9 | |
elif (face[0][0] - origin[0][0]) < 0: | |
# RIGHT motion event - A button | |
print('RIGHT') | |
return 8 | |
else: | |
# check y while x is same | |
if (face[0][1] - origin[0][1]) > 0: | |
# DOWN motion event - Q button | |
print("DOWN") | |
mouse.scroll(0, -20) | |
return 6 | |
elif (face[0][1] - origin[0][1]) < 0: | |
# UP motion event - W button | |
print('UP') | |
mouse.scroll(0, 20) | |
return 7 | |
else: | |
# possible events: Zoom in, Zoom out | |
if (face[0][2] - origin[0][2]) > 0: | |
# ZOOM IN motion event - = button | |
mouse.scroll(0, -20) | |
return 4 | |
elif (face[0][2] - origin[0][2]) < 0: | |
# ZOOM OUT motion event - -button | |
mouse.scroll(0, 20) | |
return 5 | |
if __name__ == "__main__": | |
# print('creating window' #) | |
cv2.namedWindow("Video") | |
capture = cv2.VideoCapture(CAMERA_INDEX) | |
# storage = cv.CreateMemStorage() | |
cascade = cv2.CascadeClassifier( | |
cv2.data.haarcascades + "haarcascade_frontalface_default.xml") | |
i = 0 | |
c = -1 | |
global ctr, origin, faces | |
faces = [] | |
ctr = 0 | |
origin = [] | |
while (c == -1): | |
retval, image = capture.read() | |
# print('acq img frm' #) | |
# Only run the Detection algorithm every 5 frames to improve | |
# performance | |
if i % 5 == 0: | |
# print('calling detect' #) | |
ctr += 1 | |
faces = detect_faces(image) | |
if(faces != [] and origin != []): | |
dir = get_motion(faces) | |
print(dir) | |
if ctr == 20: | |
# approx 3 secs of config time | |
origin = faces | |
print('origin is ', origin) | |
for (x, y, w, h) in faces: | |
# print('drawing rectangle' #) | |
cv2.rectangle(image, | |
(x, y), (x + w, y + h), 255) | |
# print('showing img' #) | |
cv2.imshow("Video", image) | |
# cv.ShowImage("Video", image) | |
i += 1 | |
c = cv2.waitKey(10) | |
if(c == 27): | |
# escape | |
break |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
haarcascades can be found in opencv repo, just google.