Impossibile rilevare i punti di riferimento del viso utilizzando OpenCV2
Ho sviluppato una sceneggiatura utilizzando dlib
e cv2
per disegnare punti di riferimento facciali su immagini che hanno una faccia in quell'immagine. Ecco gli script;
import cv2
import dlib
img_path = 'landmarks.png'
detector = dlib.get_frontal_face_detector()
shape_predictor = 'shape_predictor_68_face_landmarks.dat'
predictor = dlib.shape_predictor(shape_predictor)
count = 1
ready = True
while ready:
frame = cv2.imread("demo.jpg")
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
faces = detector(gray)
for face in faces:
x1 = face.left()
y1 = face.top()
x2 = face.right()
y2 = face.bottom()
cv2.rectangle(frame, (x1, y1), (x2, y2), (0, 255, 0), 3)
landmarks = predictor(gray, face)
for n in range(0, 68):
x = landmarks.part(n).x
y = landmarks.part(n).y
cv2.circle(frame, (x, y), 4, (255, 0, 0), -1)
cv2.imshow("Frame", frame)
cv2.waitKey(0)
ready = False
Ora, ecco cosa mi fa impazzire. Quando provo a scaricare una qualsiasi delle immagini (con o senza maschera) da Google per testarla, questo script funziona correttamente. Allo stesso modo, puoi vedere questi risultati come,
Ma quando provo su queste immagini seguenti, non fa nulla.
Ho effettuato un paio di ricerche su Internet ma non ho trovato nulla che serva allo scopo attuale.
Anche, ho provato la combinazione di
cv2.CascadeClassifier("haarcascade_frontalface_default.xml")
eye_cascade = cv2.CascadeClassifier('haarcascade_eye.xml')
m_cascade = cv2.CascadeClassifier('haarcascade_mcs_mouth.xml')
Ho anche esaminato i seguenti link utili là fuori;
Riquadro di delimitazione del viso
Rileva i punti di riferimento del viso in Android (anche non nello stesso dominio)
Rilevamento dei punti di riferimento
OpenCV2 rileva i punti di riferimento del viso
ma non funziona nemmeno su queste immagini. CV2 detector
mostra un elenco vuoto quando eseguo il debug tramite script come;
Voglio solo disegnare punti di riferimento fiduciali usando le immagini sopra. Quale sarebbe la migliore soluzione possibile, posso affrontare? Forse mi manca qualcosa in cv2
& Dlib
, ma non riesco a ottenere i risultati come richiesto.
Ho anche trovato il punteggio di confidenza per l' dlib
utilizzo dell'implementazione consigliata da un fanatico di Stack Overflow come;
import dlib
detector = dlib.get_frontal_face_detector()
img = dlib.load_rgb_image('demo.jpg')
dets, scores, idx = detector.run(img, 1, -1)
for i, d in enumerate(dets):
print("Detection {}, score: {}, face_type:{}".format(
d, scores[i], idx[i]))
Ecco il risultato di un punteggio di confidenza per la prima immagine nelle immagini sopra indicate nella seconda riga;
Non vedo l'ora di ottenere ricerche migliori da uno qualsiasi dei ragazzi fantastici là fuori. Grazie
Risposte
Innanzitutto, potrei provare a vedere se riesci a ottenere punteggi di confidenza da dlib. Non sono sicuro di quale sia la soglia di affidabilità, ma forse vengono rilevati volti che sono al di sotto del limite. Dal dlib Git Repo , ecco un esempio di come ottenere la sicurezza dai rilevamenti:
if (len(sys.argv[1:]) > 0):
img = dlib.load_rgb_image(sys.argv[1])
dets, scores, idx = detector.run(img, 1, -1)
for i, d in enumerate(dets):
print("Detection {}, score: {}, face_type:{}".format(
d, scores[i], idx[i]))
In alternativa, prendi in considerazione un altro rilevatore di volti, ad esempio un rilevatore basato su CNN come questo rilevatore di volti SSD MobileNet . Non ho usato questo particolare modello, ma ho usato modelli simili, come il modello di rilevatore di volti basato su Google TPU qui con ottimi risultati.
Scarica il link " shape_predictor_68_face_landmarks.dat ": inserisci qui la descrizione del link
Codice funzionante al 100% Prova questo:
import cv2
import dlib
import numpy as np
img= cv2.imread('Capture 8.PNG')
gray=cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
p = "shape_predictor_68_face_landmarks.dat"
detector = dlib.get_frontal_face_detector()
predictor = dlib.shape_predictor(p)
faces = detector(gray)
for face in faces:
x1=face.left()
y1=face.top()
x2=face.right()
y2=face.bottom()
cv2.rectangle(img, (x1,y1), (x2,y2),(0,255,0),3)
landmarks=predictor(gray, face)
for n in range(0,68):
x=landmarks.part(n).x
y=landmarks.part(n).y
cv2.circle(img, (x, y), 4, (0, 0, 255), -1)
cv2.imshow(img)