영상처리 1주차 - Face Detection(얼굴 탐지)

DatQueue·2022년 9월 21일
0
post-thumbnail

이 글은 정보 전달을 목적으로 작성된 포스팅이 아닙니다. 개인 기록으로 남기는 게시물이므로 정확한 기술적 내용관 거리가 있습니다.

1. 개발 환경 세팅


1. Visual Studio + Python + Ananconda Prompt와 Opencv

파이썬을 스스로 사용해본 적이 없고 익숙치 않아 다른 코드 에디터를 잘 모르는 관계로 익숙한 VsCode에서 진행하였다. 파이썬은 최신 버전 (3.10.7)을 설치하였다. (--> 하지만 나중에 변경할 것이므로 주의바람!!)

아직 깊게는 익히지 않았지만 영상처리하는데 필요한 모듈을 불러오기 위한 패키지를 사전에 설치해둘 필요가 있다. vsCode 터미널 창에서 아래와 같은 명령어를 통해 필요한 패키지를 설치해 보았다.


Numpy 패키지 설치

pip intall numpy

Matplotlib 설치

pip install matplotlib

OpenCV 설치

pip install opencv-python

설치 완료 확인해보기

설치 완료가 되었는지 확인하는 방법은 해당 라이브러리의 버전을 확인해보는 방법이 있다.

import cv2 as cv
print(cv.__version__)

이렇게 코드를 입력하고 터미널에 버전의 출력 결과를 확인해보면 버전이 뜰 것이라는 예상과는 다르게 "No module named cv2(cv2의 이름을 가진 모듈을 찾을 수 없습니다.)"란 문구는 물론 터미널창엔 설치된 opencv 패키지가 없다고 메시지를 주었다. ㅠㅠㅠ

한참 구글링을 해보고 삽질을 해 본 결과 다음과 같은 절차를 통해 해결하였다.

방법은 "Anaconda Prompt"를 사용해보는 것이다. 기존 Window의 명령 프롬프트를 통해 설치를 하는 방법도 있지만 Anaconda가 파이썬에선 더 강력한 IDE이기도 하다.

pip install opencv-python

Anaconda에서 기존과 동일한 위의 명령어를 작성하고 완료가 되면 아마 버전또한 바로 확인이 가능할 것이다. 사실 이미 VsCode에서도 설치를 했지만 "불러오는 과정(import module)"에서 문제가 있었다. 이것은 "버전"과 관련된 문제인 것을 확인하였다. (확실하진 않음)

파이썬에서 ctrl + shift + p 를 누르면

다음과 같은 검색창이 뜨게 된다. 이는 여러 옵션을 제어할 수 있게 해주는데 위의
"Python: Select Interpreter"를 검색창에 친 후

위와 같이 처음에 본인이 깔았던 최신 버전인 3.10.7이 아닌 Anaconda IDE가 실행되는 버전인 3.8.5로 변경해주어야 한다. 컴파일러 언어가 아닌 인터프리터언어인 파이썬에서 해당 버전 경로 설정은 생각보다 중요하다.

이제 위와 같은 과정을 끝낸 후 다시

import cv2 as cv
print(cv.__version__)

위와 같이 작성하고 결과를 확인해보면 우리가 Anaconda에서 설치해 준 opencv-python의 버전이 잘 출력될 것이다.


2. dlib 설치하기


dlib란?

이미지 처리 및 기계 학습, 얼굴인식 등을 할 수 있는 c++로 개발된 고성능의 라이브러리 (여기서 핵심은 사실 c++로 구성되었다는 것이다 ㅠㅠ)

해당 라이브러리를 이번 프로젝트에서 사용할지는 미지수이지만 일단 이 분야에 초심이고 먼저 얼굴탐지를 빠르게 느껴보기 위해 설치해보는 과정을 가지자 생각해보았다. 일반적으로 영상처리에서 opencv와 dlib 이 두 라이브러리를 함께 사용하여 성능을 극대화 한다고 한다.

설치해보기

일단 먼저 http://dlib.net/ 로 이동해 dlib 파일을 다운로드 받고 적절한 곳에 압축을 풀어주었다.(통상 C드라이브 밑에 저정을 많이 함)

그 후 그냥 아나콘다에서

pip install dlib

를 진행하였을 때 수 많은 에러를 마주하였다. 지금 뒤늦게 기록을 남겨서 에러 메시지를 캡쳐하진 못하였지만 대충 Cmake를 설치해주어야한다고 하길래 이번에는 두 가지를 동시 진행해보았다.

pip install cmake

pip install dlib

그래도 에러가 발생하였다. 에러문구는 엄청나게 길었다. 하지만 그 가운데 자세히 보면

"dlib는 c++로 만들어져있으므로 c++을 이용한 VsCode 버전을 설치할 필요가 있다."

라고 메시지를 전해주었다. dlib는 python이 아닌 c++로 작성된 라이브러리인 만큼 그에 따른 지원 버전이 필요하다는 뜻이다.

https://visualstudio.microsoft.com/ko/downloads/
해당 사이트로 들어가서


위의 무료 다운로드를 클릭한 후

설치 툴이 뜨면 워크로드로 들어가 위의 체크 표시한 "c++를 사용한 데스크톱 개발"을 클릭하면 된다.

그 후 설치가 완료되면 그냥 그걸로 끝이다. 그리고 다시 Anaconda Prompt로 들어가 명령어를 입력해 보았다. 명령어 입력은 아래로 기존과 동일하다.

pip install cmake

pip install dlib

결과는

!!! 성공적으로 dlib를 anaconda에 설치할 수 있었다.


Vscode에서 설치 확인해보기

이제 dlib를 VsCode에서 사용할 수 있는지 버전 출력을 통해 설치를 확인해보자.

import dlib
print(dlib.__version__)

터미널에서 실행해보니

다음과 같이 버전이 잘 출력되었고 dlib를 불러올 수 있게 되었다.


2. Face Detection 체험해보기

설치한 dlib와 opencv 모듈을 활용해 얼굴 감지및 특징점 분석까지 나타내 보기로 하였다. 처음인만큼 웹캠을 바로 사용하기 보단 움직이는 이미지(mp4)를 이용하여 작성해보았다.

코드에 대한 해석은 주석으로 설명하였고 자세한 opencv 및 dlib 메서드는 본인도 익숙치 않으니 구글링을 통해 찾아보면 좋을 거 같다.

코드

코드는 아래와 같다.

import cv2
import dlib
import sys
import numpy as np
from matplotlib import pyplot as plt

scaler = 0.3

detector = dlib.get_frontal_face_detector()

# 머신 러닝으로 학습된 모델
predictor = dlib.shape_predictor('shape_predictor_68_face_landmarks.dat')

cap = cv2.VideoCapture('people.mp4')

while True:
    ret, img = cap.read()
    if not ret:
        break

    img = cv2.resize(
        img, (int(img.shape[1] * scaler), int(img.shape[0] * scaler)))

    ori = img.copy()

    # detect faces
    faces = detector(img)
    face = faces[0]

    dlib_shape = predictor(img, face)
    shape_2d = np.array([[p.x, p.y] for p in dlib_shape.parts()])

    # compute center of face
    # 얼굴의 좌상단
    top_left = np.min(shape_2d, axis=0)
    # 얼굴의 우하단
    bottom_right = np.max(shape_2d, axis=0)
    # 얼굴의 중심점
    center_x, center_y = np.mean(shape_2d, axis=0).astype(np.int)

    # visualize
    img = cv2.rectangle(img, pt1=(face.left(), face.top()), pt2=(face.right(
    ), face.bottom()), color=(255, 255, 255), thickness=2, lineType=cv2.LINE_AA)

    # 얼굴 특징점 표시 (marked on face)
    for s in shape_2d:
        cv2.circle(img, center=tuple(s), radius=1, color=(
            255, 255, 255), thickness=2, lineType=cv2.LINE_AA)

    # 얼굴의 좌상단 우하단에 파랑색 특징점 표시
    cv2.circle(img, center=tuple(top_left), radius=1, color=(
        255, 0, 0), thickness=2, lineType=cv2.LINE_AA)
    cv2.circle(img, center=tuple(bottom_right), radius=1,
               color=(255, 0, 0), thickness=2, lineType=cv2.LINE_AA)

    # 얼굴의 중심에 빨간점 표시
    cv2.circle(img, center=tuple((center_x, center_y)), radius=1,
               color=(0, 0, 255), thickness=2, lineType=cv2.LINE_AA)

    cv2.imshow('img', img)
    cv2.waitKey(1)

결과 분석 및 간단한 고찰

결과를 확인해보자.

결과를 확인해보니 아직 정확히 코드에 대해 분석이 덜 되어서 그런지 두 얼굴을 동시 탐지하는 것이나 혹은 얼굴이 어느 정도 가려지는 것에 대해서 탐지를 못하는 경우가 발생하였다. 이것에 대해 조금 더 알아보는 과정이 필요하고 어떻게 조금 더 깔끔하게 얼굴을 인식할 수 있을 지 논의해 봐야할 것 같다.


진행 상태 캡쳐

profile
You better cool it off before you burn it out / 티스토리(Kotlin, Android): https://nemoo-dev.tistory.com

0개의 댓글