Aujourd'hui, nous allons l'étendre et jouer à des combats d'avions avec des visages humains. Bien que l'idée soit similaire à la reconnaissance gestuelle, la quantité de code est légèrement supérieure à celle de la version à reconnaissance gestuelle.
L'algorithme de visage utilisé est de niveau milliseconde, la fréquence d'images peut atteindre 30 et il fonctionne très bien sur le processeur d'un ordinateur.
Maintenant, je vais partager le processus de mise en œuvre du projet et obtenir le code source complet du projet à la fin de l'article.
Trouvez une version Python du programme de guerre des avions sur Github, installez Pygame et exécutez-le.
Utilisez les touches A, D, W et S du clavier pour contrôler la direction du mouvement de l'avion, qui correspondent respectivement à gauche, droite, haut et bas.
Donc, ce que nous devons faire ensuite, c'est reconnaître le visage, estimer la pose du visage et cartographier les résultats estimés à gauche, à droite, en haut et en bas pour contrôler le fonctionnement de l'avion.
Ici, nous utilisons opencv pour lire le flux vidéo de la caméra.
Envoyez chaque image du flux vidéo au modèle de reconnaissance faciale dans Mediapipe pour reconnaissance.
Picture Mediapipe peut non seulement reconnaître les visages, mais également marquer 6 points clés sur les visages : œil gauche, œil droit, oreille gauche, oreille droite, nez et bouche.
Code principal :
with self.mp_face_detection.FaceDetection( model_selection=0, min_detection_confidence=0.9) as face_detection: while cap.isOpened(): success, image = cap.read() image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB) results = face_detection.process(image) image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR) if results.detections: for detection in results.detections: # 获取人脸框坐标 face_box = detection.location_data.relative_bounding_box face_w, face_h = int(face_box.width * frame_w), int(face_box.height * frame_h) face_l = int(face_box.xmin * frame_w) + face_w face_t = int(face_box.ymin * frame_h) face_r, face_b = face_l - face_w, face_t + face_h # 显示人脸框 cv2.rectangle(image, (face_l, face_t), (face_r, face_b), (0, 255, 255), 2) self.draw_zh_img(image, self.face_box_name_img, (face_r + face_l) // 2, face_t - 5) pose_direct, pose_key_points = self.pose_estimate(detection) # 显示人脸 6 个关键点 for point_name in FaceKeyPoint: mp_point = self.mp_face_detection.get_key_point(detection, point_name) point_x = int(mp_point.x * frame_w) point_y = int(mp_point.y * frame_h) point_color = (0, 255, 0) if point_name in pose_key_points else (255, 0, 255) cv2.circle(image, (point_x, point_y), 4, point_color, -1) # 显示关键点中文名称 point_name_img = self.face_key_point_name_img[point_name] self.draw_zh_img(image, point_name_img, point_x, point_y-5)
Il y a un petit point de connaissance auquel tout le monde doit prêter attention.
Draw_zh_img est utilisé dans le code pour afficher le chinois, car opencv ne prend pas en charge l'affichage direct du chinois. Par conséquent, j'utilise la méthode Image dans le module PIL pour dessiner des images chinoises à l'avance et les convertir au format opencv.
En cas de besoin, fusionnez directement avec le flux vidéo, avec une grande efficacité et sans perte d'image.
Avant la reconnaissance des gestes, nous utilisions des images adjacentes pour juger du mouvement des gestes. L'estimation de la pose du visage utilise uniquement l'image actuelle, ce qui est relativement simple.
On peut déterminer la posture du visage grâce à la distance coordonnée des 6 points clés du visage
Ici, la distance horizontale entre l'oreille gauche et le nez est très proche, on peut donc estimer que le visage tourne vers la gauche, vous ne pouvez donc utiliser que l'avion pour vous déplacer vers la gauche.
De même, en utilisant d'autres points clés, nous pouvons estimer si le visage tourne vers la droite, vers le haut (lever la tête) et vers le bas (baisser la tête). posture du visage, nous pouvons utiliser le programme pour contrôler le clavier afin de contrôler le mouvement de l'avion.
Ici, j'utilise le module PyKeyboard pour contrôler les touches du clavier. Les fonctions
# 左耳与鼻子水平距离,判断面部左转 left_ear_to_nose_dist = left_ear.x - nose_pos.x # 右耳与鼻子水平距离,判断面部右转 nose_to_right_ear_dist = nose_pos.x - right_ear.x # 鼻子与左眼垂直距离,判断面部向上 nose_to_left_eye_dist = nose_pos.y - left_eye.y # 左耳与左眼垂直距离,判断面部向下 left_ear_to_left_eye_dist = left_ear.y - left_eye.y if left_ear_to_nose_dist < 0.07: # print('左转') self.key_board.press_key('A') time.sleep(0.07) self.key_board.release_key('A') return 'A', [FaceKeyPoint.NOSE_TIP, FaceKeyPoint.LEFT_EAR_TRAGION] if nose_to_right_ear_dist < 0.07: # print('右转') self.key_board.press_key('D') time.sleep(0.07) self.key_board.release_key('D') return 'D', [FaceKeyPoint.NOSE_TIP, FaceKeyPoint.RIGHT_EAR_TRAGION]
Entre eux, time.sleep(0.07) est appelé pour contrôler la durée du bouton. Si le bouton est enfoncé longtemps, la distance parcourue par l'avion sera longue. Au contraire, si le bouton time est long. Courte, la distance parcourue par l'avion sera courte. Vous pouvez l'ajuster en fonction de vos propres besoins.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!