OpenCV实现人脸检测和68点定位
人臉對比是現在比較常用的功能,比如出租車司機人臉與司機駕照照片對比,門禁系統中進入者的人臉與人臉庫中的人臉進行對比。要實現人臉對比,首先要實現的是人臉檢測,在攝像頭拍攝到的一張圖片中,正確的檢測到人臉的位置,并且將人臉提取出來。
目錄
1 原理先知
? ? ? ??1.1 68點標定和OpenCV繪點
? ? ? ??1.2 編碼設計思路
? ? ? ??1.3 OpenCV畫圖函數介紹
2 環境說明
3 實驗內容
4 步驟詳解
? ? ? ??4.1 OpenCV實現人臉檢測
? ? ? ??4.2 人臉68點定位
1 原理先知
1.1 68點標定和OpenCV繪點
考慮到免費開源,OpenCV 就可以很好的實現這個功能。
這里使用OpenCV提供好的人臉分類模型xml:haarcascade_frontalface_alt_tree.xml。
同時利用Dlib官方給的人臉識別預測器“shape_predictor_68_face_landmarks.dat”進行68點標定(利用OpenCV進行圖像化處理,在人臉上畫出68個點,并標明序號)。
注:OpenCV人臉分類模型xml及Dlib人臉識別預測器下載地址
https://pan.baidu.com/s/1gZfYupoW9Zo_2lVV524cWA?
提取碼:w536?
人臉68點定位工作內容主要以下兩大塊:68點標定 和 OpenCV繪點
- 68點標定:dlib提供了訓練好的模型,可以識別人臉的68個特征點
- OpenCV繪點:畫圓函數cv2.circle() 和 輸出字符串函數 cv2.putText()
1.2 編碼設計思路
- 調用dlib庫來進行人臉識別,調用預測器“shape_predictor_68_face_landmarks.dat”
- 進行68點標定存入68個點坐標
- 利用cv2.circle來畫68個點
- 利用cv2.putText()函數來畫數字1-68
1.3 OpenCV畫圖函數介紹
img 圖片對象
(p1,p2) 圓心坐標
r 半徑
(255,255,255)? 顏色數組
img 圖像對象
"test"? 需要打印的字符 text(數字的話可以利用str()轉成字符)
(p1,p2) 坐標 textOrg
font 表示字體 fontFace(注意這里 font = cv2.FONT_HERSHEY_SIMPLEX)
4 表示字號 fontScale
(255,255,255) 顏色數組
2 線寬 thickness
LINE_AA 線條種類 line_type;
關于顏色數組:(255,255,255), (藍色,綠色,紅色),每個值都是0-255。比如:藍色(255,0,0),紫色(255,0,255)
2 環境說明
- Linux Ubuntu 16.04
- Python 3.6
- PyCharm Community2018
- Opencv-python 3.4.0.12
3 實驗內容
4 步驟詳解
4.1 OpenCV實現人臉檢測
首先將圖片轉換成灰色:使用 OpenCV 的 cvtColor() 轉換圖片顏色。
import cv2 filepath = "/data/opencv12/mv.jpg" img = cv2.imread(filepath) # 轉換灰色,目的是在人臉檢測時排除色彩的干擾 gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 顯示圖像 cv2.imshow("original", img) cv2.imshow("Image", gray) cv2.waitKey(0) cv2.destroyAllWindows()之后使用訓練分類器查找人臉:在使用 OpenCV 的人臉檢測之前,需要一個人臉訓練模型,格式是 xml 的,本實驗中使用的是 OpenCV 提供好的人臉分類模型 xml:haarcascade_frontalface_alt_tree.xml。
Haar 特征分類器就是一個 XML 文件,該文件中會描述人體各個部位的Haar特征值。包括人臉、眼睛、嘴唇等等。
OpenCV中人臉檢測使用的是 detectMultiScale函數。它可以檢測出圖片中所有的人臉,并將人臉用vector保存各個人臉的坐標、大小(用矩形表示)。
最后在圖片上畫矩形:使用 OpenCV 的 rectangle() 繪制矩形。
color = (0, 255, 0) if len(faceRects): # 大于0則檢測到人臉 for faceRect in faceRects: # 單獨框出每一張人臉 x, y, w, h = faceRect # x、y表示坐標;w、h表示矩形寬和高 # 框出人臉 cv2.rectangle(img, (x, y), (x + h, y + w), color, 2) # 左眼 cv2.circle(img, (x + w // 4, y + h // 4 + 30), min(w // 8, h // 8),color) #右眼 cv2.circle(img, (x + 3 * w // 4, y + h // 4 + 30), min(w // 8, h // 8),color) #嘴巴 cv2.rectangle(img, (x + 3 * w // 8, y + 3 * h // 4),(x + 5 * w // 8, y + 7 * h // 8), color)OpenCV實現人臉檢測完整代碼如下:
import cv2 filepath = "/data/opencv12/mv.jpg" img = cv2.imread(filepath) cv2.imshow("original", img) gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) classifier = cv2.CascadeClassifier("/data/opencv12/haarcascade_frontalface_alt_tree.xml") faceRects = classifier.detectMultiScale(gray, scaleFactor=1.2, minNeighbors=3, minSize=(32, 32)) color = (0, 255, 0) if len(faceRects): for faceRect in faceRects: x, y, w, h = faceRect cv2.rectangle(img, (x, y), (x + h, y + w), color, 2) cv2.circle(img, (x + w // 4, y + h // 4 + 30), min(w // 8, h // 8),color) cv2.circle(img, (x + 3 * w // 4, y + h // 4 + 30), min(w // 8, h // 8),color) cv2.rectangle(img, (x + 3 * w // 8, y + 3 * h // 4),(x + 5 * w // 8, y + 7 * h // 8), color) cv2.imshow("image", img) cv2.waitKey(0) cv2.destroyAllWindows()OpenCV實現人臉檢測運行結果如下所示。
4.2 人臉68點定位
除了使用 OpenCV 實現人臉檢測之外,也可以借助比 OpenCV 更加精準的圖片人臉檢測 Dlib 庫實現人臉 68 點定位。
首先導入需要調用的庫。
import dlib #人臉識別的庫dlib from PIL import Image #圖像處理的庫PIL import numpy as np #數據處理的庫numpy import cv2 #圖像處理的庫OpenCv之后讀取圖片,并將圖片轉換為灰度圖。
path = "/data/opencv12/mv.jpg" img = cv2.imread(path) cv2.imshow("original", img) gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)接下來讀取訓練模型,就可以檢測臉部 68 特征點。
# 人臉分類器 detector = dlib.get_frontal_face_detector() # 獲取人臉檢測器 predictor = dlib.shape_predictor("/data/opencv12/shape_predictor_68_face_landmarks.dat")最后在人臉上遍歷所有檢測點并打上標注,并標注 1-68 數字。
rects = detector(gray, 0) for i in range(len(rects)): landmarks = np.matrix([[p.x, p.y] for p in predictor(img, rects[i]).parts()]) # 尋找人臉的68個標定點 # 遍歷所有點,打印出其坐標,并圈出來,并標注1-68數字 for idx, point in enumerate(landmarks): pos = (point[0, 0], point[0, 1]) # 利用cv2.circle給每個特征點畫一個圈,共68個 cv2.circle(img, pos, 3, color=(0, 255, 0)) # 利用cv2.putText輸出1-68 font = cv2.FONT_HERSHEY_SIMPLEX cv2.putText(img, str(idx+1), pos, font, 0.3, (0, 0, 255), 1, cv2.LINE_AA)人臉68點定位完整代碼如下:
import cv2 import dlib import numpy as np path = "/data/opencv12/mv.jpg" img = cv2.imread(path) cv2.imshow("original", img) gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) detector = dlib.get_frontal_face_detector() predictor = dlib.shape_predictor("/data/opencv12/shape_predictor_68_face_landmarks.dat") rects = detector(gray, 0) for i in range(len(rects)): landmarks = np.matrix([[p.x, p.y] for p in predictor(img, rects[i]).parts()]) for idx, point in enumerate(landmarks): pos = (point[0, 0], point[0, 1]) cv2.circle(img, pos, 3, color=(0, 255, 0)) font = cv2.FONT_HERSHEY_SIMPLEX cv2.putText(img, str(idx+1), pos, font, 0.3, (0, 0, 255), 1, cv2.LINE_AA) cv2.imshow("imgdlib", img) cv2.waitKey(0) cv2.destroyAllWindows()人臉68點定位運行結果如下所示。
可以發現,dlib檢測到人臉包括雙眼、鼻子、嘴巴在內并用68點標注過的圖片如下所示,并可以精準的定位檢測人臉。
歡迎留言,一起學習交流~
感謝閱讀
END
總結
以上是生活随笔為你收集整理的OpenCV实现人脸检测和68点定位的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: h5-(安卓和ios)之间的传值
- 下一篇: 人脸识别门锁实现