国产毛片a精品毛-国产毛片黄片-国产毛片久久国产-国产毛片久久精品-青娱乐极品在线-青娱乐精品

如何用OpenCV進行人臉疲勞檢測--基于米爾瑞芯微RK3576開發板

發布時間:2024-12-19 11:37    發布者:swiftman
本篇源自:優秀創作者 lulugl

本文將介紹基于米爾電子MYD-LR3576開發板(米爾基于瑞芯微 RK3576開發板)的人臉疲勞檢測方案測試。
米爾基于RK3576核心板/開發板
【前言】
人臉疲勞檢測:一種通過分析人臉特征來判斷一個人是否處于疲勞狀態的技術。其原理主要基于計算機視覺和機器學習方法。當人疲勞時,面部會出現一些特征變化,如眼睛閉合程度增加、眨眼頻率變慢、打哈欠、頭部姿態改變等。
例如,通過檢測眼睛的狀態來判斷疲勞程度是一個關鍵部分。正常情況下,人的眨眼頻率相對穩定,而當疲勞時,眨眼頻率會降低,并且每次眨眼時眼睛閉合的時間可能會延長。同時,頭部可能會不自覺地下垂或者搖晃,這些特征都可以作為疲勞檢測的依據。米爾MYC-LR3576采用8核CPU+搭載6 TOPS的NPU加速器,3D GPU,能夠非常輕松的實現這個功能,下面就如何實現這一功能分享如下:
【硬件】
1、米爾MYC-LR3576開發板
2、USB攝像頭
【軟件】
1、v4l2
2、openCV
3、dlib庫:dlib 是一個現代化的 C++ 工具包,它包含了許多用于機器學習、圖像處理、數值計算等多種任務的算法和工具。它的設計目標是提供高性能、易于使用的庫,并且在開源社區中被廣泛應用。
【實現步驟】
1、安裝python-opencv
2、安裝dlib庫
3、安裝v4l2庫
代碼實現】
1、引入cv2、dlib以及線程等:
  1. import cv2
  2. import dlib
  3. import numpy as np
  4. import time
  5. from concurrent.futures import ThreadPoolExecutor
  6. import threading
復制代碼

2、初始化dlib的面部檢測器和特征點預測器
  1. detector = dlib.get_frontal_face_detector()
  2. predictor = dlib.shape_predictor('shape_predictor_68_face_landmarks.dat')
復制代碼

3、定義計算眼睛縱橫比的函數
  1. def eye_aspect_ratio(eye):
  2.     A = np.linalg.norm(np.array(eye[1]) - np.array(eye[5]))
  3.     B = np.linalg.norm(np.array(eye[2]) - np.array(eye[4]))
  4.     C = np.linalg.norm(np.array(eye[0]) - np.array(eye[3]))
  5.     ear = (A + B) / (2.0 * C)                                                                                
  6.     return ear
復制代碼

4、定義計算頭部姿勢的函數
  1. def get_head_pose(shape):
  2.     # 定義面部特征點的三維坐標
  3.     object_points = np.array([
  4.         (0.0, 0.0, 0.0),             # 鼻尖
  5.         (0.0, -330.0, -65.0),        # 下巴
  6.         (-225.0, 170.0, -135.0),     # 左眼左眼角
  7.         (225.0, 170.0, -135.0),      # 右眼右眼角
  8.         (-150.0, -150.0, -125.0),    # 左嘴角
  9.         (150.0, -150.0, -125.0)      # 右嘴角
  10.     ], dtype=np.float32)

  11.     image_pts = np.float32([shape[i] for i in [30, 8, 36, 45, 48, 54]])
  12.     size = frame.shape
  13.     focal_length = size[1]
  14.     center = (size[1] // 2, size[0] // 2)
  15.     camera_matrix = np.array(
  16.         [[focal_length, 0, center[0]],
  17.          [0, focal_length, center[1]],
  18.          [0, 0, 1]], dtype="double"
  19.     )

  20.     dist_coeffs = np.zeros((4, 1))
  21.     (success, rotation_vector, translation_vector) = cv2.solvePnP(
  22.         object_points, image_pts, camera_matrix, dist_coeffs, flags=cv2.SOLVEPNP_ITERATIVE
  23.     )

  24.     rmat, _ = cv2.Rodrigues(rotation_vector)
  25.     angles, _, _, _, _, _ = cv2.RQDecomp3x3(rmat)
  26.     return angles
復制代碼

5、定義眼睛縱橫比閾值和連續幀數閾值
  1. EYE_AR_THRESH = 0.3
  2. EYE_AR_CONSEC_FRAMES = 48
復制代碼

6、打開攝像頭
我們先使用v4l2-ctl --list-devices來例出接在開發板上的列表信息:
  1. USB Camera: USB Camera (usb-xhci-hcd.0.auto-1.2):
  2.         /dev/video60
  3.         /dev/video61
  4.         /dev/media7
復制代碼

在代碼中填入60為攝像頭的編號:
  1. cap = cv2.VideoCapture(60)
  2. cap.set(cv2.CAP_PROP_FRAME_WIDTH, 480)  # 降低分辨率
  3. cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 320)
復制代碼

7、創建多線程處理函數,實現采集與分析分離:
  1. # 多線程處理函數
  2. def process_frame(frame):
  3.     global COUNTER, TOTAL
  4.     gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
  5.     faces = detector(gray, 0)  # 第二個參數為0,表示不使用upsampling

  6.     for face in faces:
  7.         landmarks = predictor(gray, face)
  8.         shape = [(landmarks.part(i).x, landmarks.part(i).y) for i in range(68)]
  9.         
  10.         left_eye = shape[36:42]
  11.         right_eye = shape[42:48]

  12.         left_ear = eye_aspect_ratio(left_eye)
  13.         right_ear = eye_aspect_ratio(right_eye)
  14.         ear = (left_ear + right_ear) / 2.0

  15.         if ear < EYE_AR_THRESH:
  16.             with lock:
  17.                 COUNTER += 1
  18.         else:
  19.             with lock:
  20.                 if COUNTER >= EYE_AR_CONSEC_FRAMES:
  21.                     TOTAL += 1
  22.                 COUNTER = 0

  23.         # 繪制68個特征點
  24.         for n in range(0, 68):
  25.             x, y = shape[n]
  26.             cv2.circle(frame, (x, y), 2, (0, 255, 0), -1)

  27.         cv2.putText(frame, f"Eye AR: {ear:.2f}", (10, 30), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  28.         cv2.putText(frame, f"Blink Count: {TOTAL}", (10, 60), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  29.         # 計算頭部姿勢
  30.         angles = get_head_pose(shape)
  31.         pitch, yaw, roll = angles
  32.         cv2.putText(frame, f"Pitch: {pitch:.2f}", (10, 120), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  33.         cv2.putText(frame, f"Yaw: {yaw:.2f}", (10, 150), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  34.         cv2.putText(frame, f"Roll: {roll:.2f}", (10, 180), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  35.         # 判斷疲勞狀態
  36.         if COUNTER >= EYE_AR_CONSEC_FRAMES or abs(pitch) > 30 or abs(yaw) > 30 or abs(roll) > 30:
  37.             cv2.putText(frame, "Fatigue Detected!", (10, 210), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  38.     return frame
復制代碼
8、創建圖像顯示線程:
  1. with ThreadPoolExecutor(max_workers=2) as executor:
  2.     future_to_frame = {}
  3.     while True:
  4.         ret, frame = cap.read()
  5.         if not ret:
  6.             break

  7.         # 提交當前幀到線程池
  8.         future = executor.submit(process_frame, frame.copy())
  9.         future_to_frame[future] = frame

  10.         # 獲取已完成的任務結果
  11.         for future in list(future_to_frame.keys()):
  12.             if future.done():
  13.                 processed_frame = future.result()
  14.                 cv2.imshow("Frame", processed_frame)
  15.                 del future_to_frame[future]
  16.                 break

  17.         # 計算幀數
  18.         fps_counter += 1
  19.         elapsed_time = time.time() - start_time
  20.         if elapsed_time > 1.0:
  21.             fps = fps_counter / elapsed_time
  22.             fps_counter = 0
  23.             start_time = time.time()
  24.             cv2.putText(processed_frame, f"FPS: {fps:.2f}", (10, 90), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)

  25.         if cv2.waitKey(1) & 0xFF == ord('q'):
復制代碼

實現效果:

根據檢測的結果,我們就可以來實現疲勞提醒等等的功能。
整體代碼如下:
  1. import cv2
  2. import dlib
  3. import numpy as np
  4. import time
  5. from concurrent.futures import ThreadPoolExecutor
  6. import threading

  7. # 初始化dlib的面部檢測器和特征點預測器
  8. detector = dlib.get_frontal_face_detector()
  9. predictor = dlib.shape_predictor('shape_predictor_68_face_landmarks.dat')

  10. # 修改字體大小
  11. font_scale = 0.5  # 原來的字體大小是0.7,現在改為0.5

  12. # 定義計算眼睛縱橫比的函數
  13. def eye_aspect_ratio(eye):
  14.     A = np.linalg.norm(np.array(eye[1]) - np.array(eye[5]))
  15.     B = np.linalg.norm(np.array(eye[2]) - np.array(eye[4]))
  16.     C = np.linalg.norm(np.array(eye[0]) - np.array(eye[3]))
  17.     ear = (A + B) / (2.0 * C)                                                                                
  18.     return ear

  19. # 定義計算頭部姿勢的函數
  20. def get_head_pose(shape):
  21.     # 定義面部特征點的三維坐標
  22.     object_points = np.array([
  23.         (0.0, 0.0, 0.0),             # 鼻尖
  24.         (0.0, -330.0, -65.0),        # 下巴
  25.         (-225.0, 170.0, -135.0),     # 左眼左眼角
  26.         (225.0, 170.0, -135.0),      # 右眼右眼角
  27.         (-150.0, -150.0, -125.0),    # 左嘴角
  28.         (150.0, -150.0, -125.0)      # 右嘴角
  29.     ], dtype=np.float32)

  30.     image_pts = np.float32([shape[i] for i in [30, 8, 36, 45, 48, 54]])
  31.     size = frame.shape
  32.     focal_length = size[1]
  33.     center = (size[1] // 2, size[0] // 2)
  34.     camera_matrix = np.array(
  35.         [[focal_length, 0, center[0]],
  36.          [0, focal_length, center[1]],
  37.          [0, 0, 1]], dtype="double"
  38.     )

  39.     dist_coeffs = np.zeros((4, 1))
  40.     (success, rotation_vector, translation_vector) = cv2.solvePnP(
  41.         object_points, image_pts, camera_matrix, dist_coeffs, flags=cv2.SOLVEPNP_ITERATIVE
  42.     )

  43.     rmat, _ = cv2.Rodrigues(rotation_vector)
  44.     angles, _, _, _, _, _ = cv2.RQDecomp3x3(rmat)
  45.     return angles

  46. # 定義眼睛縱橫比閾值和連續幀數閾值
  47. EYE_AR_THRESH = 0.3
  48. EYE_AR_CONSEC_FRAMES = 48

  49. # 初始化計數器
  50. COUNTER = 0
  51. TOTAL = 0

  52. # 創建鎖對象
  53. lock = threading.Lock()

  54. # 打開攝像頭
  55. cap = cv2.VideoCapture(60)
  56. cap.set(cv2.CAP_PROP_FRAME_WIDTH, 480)  # 降低分辨率
  57. cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 320)

  58. # 初始化幀計數器和時間戳
  59. fps_counter = 0
  60. start_time = time.time()

  61. # 多線程處理函數
  62. def process_frame(frame):
  63.     global COUNTER, TOTAL
  64.     gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
  65.     faces = detector(gray, 0)  # 第二個參數為0,表示不使用upsampling

  66.     for face in faces:
  67.         landmarks = predictor(gray, face)
  68.         shape = [(landmarks.part(i).x, landmarks.part(i).y) for i in range(68)]
  69.         
  70.         left_eye = shape[36:42]
  71.         right_eye = shape[42:48]

  72.         left_ear = eye_aspect_ratio(left_eye)
  73.         right_ear = eye_aspect_ratio(right_eye)
  74.         ear = (left_ear + right_ear) / 2.0

  75.         if ear < EYE_AR_THRESH:
  76.             with lock:
  77.                 COUNTER += 1
  78.         else:
  79.             with lock:
  80.                 if COUNTER >= EYE_AR_CONSEC_FRAMES:
  81.                     TOTAL += 1
  82.                 COUNTER = 0

  83.         # 繪制68個特征點
  84.         for n in range(0, 68):
  85.             x, y = shape[n]
  86.             cv2.circle(frame, (x, y), 2, (0, 255, 0), -1)

  87.         cv2.putText(frame, f"Eye AR: {ear:.2f}", (10, 30), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  88.         cv2.putText(frame, f"Blink Count: {TOTAL}", (10, 60), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  89.         # 計算頭部姿勢
  90.         angles = get_head_pose(shape)
  91.         pitch, yaw, roll = angles
  92.         cv2.putText(frame, f"Pitch: {pitch:.2f}", (10, 120), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  93.         cv2.putText(frame, f"Yaw: {yaw:.2f}", (10, 150), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)
  94.         cv2.putText(frame, f"Roll: {roll:.2f}", (10, 180), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  95.         # 判斷疲勞狀態
  96.         if COUNTER >= EYE_AR_CONSEC_FRAMES or abs(pitch) > 30 or abs(yaw) > 30 or abs(roll) > 30:
  97.             cv2.putText(frame, "Fatigue Detected!", (10, 210), cv2.FONT_HERSHEY_SIMPLEX, font_scale, (0, 0, 255), 2)

  98.     return frame

  99. with ThreadPoolExecutor(max_workers=2) as executor:
  100.     future_to_frame = {}
  101.     while True:
  102.         ret, frame = cap.read()
  103.         if not ret:
  104.             break

  105.         # 提交當前幀到線程池
  106.         future = executor.submit(process_frame, frame.copy())
  107.         future_to_frame[future] = frame

  108.         # 獲取已完成的任務結果
  109.         for future in list(future_to_frame.keys()):
  110.             if future.done():
  111.                 processed_frame = future.result()
  112.                 cv2.imshow("Frame", processed_frame)
  113.                 del future_to_frame[future]
  114.                 break

  115.         # 計算幀數
  116.         fps_counter += 1
  117.         elapsed_time = time.time() - start_time
  118.         if elapsed_time > 1.0:
  119.             fps = fps_counter / elapsed_time
  120.             fps_counter = 0
  121.             start_time = time.time()
  122.             cv2.putText(processed_frame, f"FPS: {fps:.2f}", (10, 90), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)

  123.         if cv2.waitKey(1) & 0xFF == ord('q'):
  124.             break

  125. # 釋放攝像頭并關閉所有窗口
  126. cap.release()
  127. cv2.destroyAllWindows()
復制代碼

【總結】
【米爾MYC-LR3576核心板及開發板】
這塊開發板性能強大,能輕松實現對人臉的疲勞檢測,通過計算結果后進入非常多的工業、人工智能等等的實用功能。
本文地址:http://m.qingdxww.cn/thread-878896-1-1.html     【打印本頁】

本站部分文章為轉載或網友發布,目的在于傳遞和分享信息,并不代表本網贊同其觀點和對其真實性負責;文章版權歸原作者及原出處所有,如涉及作品內容、版權和其它問題,我們將根據著作權人的要求,第一時間更正或刪除。
您需要登錄后才可以發表評論 登錄 | 立即注冊

廠商推薦

  • Microchip視頻專區
  • PIC32CM LS00 Curiosity Pro評估工具包
  • 探索PIC16F13145 MCU系列——快速概覽
  • dsPIC® DSC:攻克各種觸摸傳感挑戰的電容式觸摸解決方案
  • PIC32CM LS60 Curiosity Pro評估工具包
  • 貿澤電子(Mouser)專區

相關視頻

關于我們  -  服務條款  -  使用指南  -  站點地圖  -  友情鏈接  -  聯系我們
電子工程網 © 版權所有   京ICP備16069177號 | 京公網安備11010502021702
快速回復 返回頂部 返回列表
主站蜘蛛池模板: 日本三级2020| 欧美一级免费观看| 日韩理论片在线看免费观看| 欧美亚洲不卡| 四虎永久在线精品国产| 午夜精品久久久久久| 日本中文字幕一区二区有码在线| 天天看毛片| 色综合久久88色综合天天小说| 手机看片久久国产免费不卡| 四虎影院黄色| 天天偷窥网| 亚洲国产精品一区二区第四页| 人人人人凹人人爽人人澡| 人人搞人人爱| 秀逼逼| 色综合91久久精品中文字幕| 涩涩涩综合在线亚洲第一| 亚洲免费一区二区| 奇米影视国产精品四色| 亚洲精美视频| 香蕉碰碰| 青草国产精品久久久久久| 西西人体444www免费| 日韩麻豆国产精品欧美| 日韩成人动漫| 性短视频在线观看免费不卡流畅| 亚洲欧洲国产成人综合一本| 日韩午夜免费视频| 日韩福利视频高清免费看| 三a级毛片| 特级毛片免费视频观看| 无遮挡中文毛片免费观看| 日本免费观看的视频在线| 日韩一中文字幕| 欧美自拍偷拍视频| 日韩欧美一区二区三区免费观看| 性色欧美xo影院| 亚洲天堂视频在线播放| 亚洲综合国产一区在线| 香港日本韩国三级网站|