곰퓨타의 SW 이야기

[python] dlib을 통한 얼굴 인식 및 landmark 찾기 본문

Project/2d face to 3d face reconstruction

[python] dlib을 통한 얼굴 인식 및 landmark 찾기

곰퓨타 2021. 5. 10. 17:03

dlib cnn_face_detection_model_v1은 dlib 19.5부터 된다는 점에 주의해야 한다.

 

아래 코드는 image path를 주었을 때 해당 폴더에 있는 image를 수집하여 사람을 detect하고 , 68 face landmark를 통해 얼굴의 5부분(right eye, left eye, nose tip, right mouth corner and left mouth corner)을 txt 파일에 저장한다.

 

한 사진에 여러명의 사람이 나타나는 경우 000001-1.txt 와 같은 방식으로 작성하여 텍스트 파일을 저장하도록 하였다.

 

github.com/microsoft/Deep3DFaceReconstruction

 

microsoft/Deep3DFaceReconstruction

Accurate 3D Face Reconstruction with Weakly-Supervised Learning: From Single Image to Image Set (CVPRW 2019) - microsoft/Deep3DFaceReconstruction

github.com

이 코드를 수행하기 위해 custom data를 preprocessing 하기 위하여 고안하였다.

 

github.com/microsoft/Deep3DFaceReconstruction/issues/38

 

How to get the 5 landmarks for my own image set? · Issue #38 · microsoft/Deep3DFaceReconstruction

Hi, thanks for your contribution. And I have a question, in my own image set, how to get the 5 landmarks for every image? (obtain by other face detect network like MTCNN??)

github.com

이는 issue에 있는 것을 보고 응용하여 작성하였다.

 

 

import dlib
import cv2
from imutils import face_utils
import argparse
from utils import *
import os
import glob

def parse_args():
    desc = "Data preprocessing for Deep3DRecon."
    parser = argparse.ArgumentParser(description=desc)

    parser.add_argument('--img_path', type=str, default='./input', help='original images folder')
    parser.add_argument('--save_path', type=str, default='./processed_data', help='custom path to save proccessed images and labels')


    return parser.parse_args()

def midpoint(p1, p2):
    coords = (p1[0] + p2[0]) / 2, (p1[1] + p2[1]) / 2
    return [int(x) for x in coords]

def preprocessing():
    args = parse_args()
    image_path = args.img_path
    save_path = args.save_path

    img_list = sorted(glob.glob(image_path + '/' + '*.png'))
    img_list += sorted(glob.glob(image_path + '/' + '*.jpg'))

    detector = dlib.get_frontal_face_detector()
    predictor = dlib.shape_predictor('shape_predictor_68_face_landmarks.dat')


    for file in img_list:
        img = cv2.imread(file)

        gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
        # 1하니까 갑자기 여러명 detect 됨
        rects = detector(gray, 1)

        count =1

        if len(rects) > 0:
            for rect in rects:
                x = rect.left()
                y = rect.top()
                w = rect.right()
                h = rect.bottom()
                # crop = img[y:h, x:w]

                # shape = predictor(crop, rect)
                shape = predictor(img, rect)
                shape_np = face_utils.shape_to_np(shape).tolist()
                left_eye = midpoint(shape_np[36], shape_np[39])
                right_eye = midpoint(shape_np[42], shape_np[45])
                features = [left_eye, right_eye, shape_np[33], shape_np[48], shape_np[54]]


                cv2.imwrite(file.split('.')[0]+'-'+str(count)+'.jpg',img)

                with open(file.split('.')[0]+'-'+str(count) + ".txt", "a") as f:
                    for i in features:
                        print(str(i[0]) + ' ' + str(i[1]), file=f)
                count += 1


if __name__ == '__main__':
	preprocessing()
Comments