소프트웨어 프로젝트2 과목의 Adventure Design을 위한 보고서입니다.
주제 : 얼굴 인식을 통한 유사도 측정
얼굴 인식을 이용해서 연예인과의 얼굴 유사도를 분석하고 표로 나타내보자.
- 노트북에 내장된 전면카메라를 이용해 사진을 찍어 자신의 얼굴의 학습데이터를 만든다.
- 학습된 데이터를 바탕으로 얼굴 인식 AI를 만든다.
- AI가 DB에 저장된 연예인 사진들을 얼굴 인식 AI에 입력으로 하여 어느정도 유사도가 나오는지 계산하고 저장한다.
- 저장한 데이터를 python의 matplotlib를 통해 그래프를 그린다.
- python의 pyqt가 제공하는 GUI를 통해 만들어진 그래프를 표시한다.
- 클릭 시 추가적인 정보(비교에 사용된 연예인 사진)를 확인할 수 있는 기능 구현
- 자신이 가지고 있는 사진도 등록해서 그 사람과의 유사도를 측정할 수 있는 기능 구현.
이미지 가공 알고리즘(차용), 학습 알고리즘(차용), DB(AI 데이터, 연예인 사진 저장, 분석 결과 저장), matplotlib를 이용한 그래프 구현 알고리즘, pyqt GUI 코드 파일 통합, 유저 친화적인 인터페이스 개발
모듈 | 클래스 | 역할 |
---|---|---|
Facial_Recognition.py | FaceRecognition | 유저의 얼굴을 바탕으로 머신러닝 학습을 하고 학습된 AI를 이용해 유저의 얼굴과 연예인 얼굴을 비교해 유사율을 측정한다. |
FaceCapture | 기본 값으로 지정되어 있는 카메라를 통해 얼굴 사진을 찍고 유저마다 유저의 사진을 저장하는 폴더를 만든다. | |
Graph.py | Button | 버튼의 생성과 이벤트 메소드와의 연결을 한 번에 해준다. |
BarGraph | 유저와 연예인과의 얼굴 유사도가 저장되어 있는 딕셔너리를 받고 상위 10개를 뽑아 matplotlib를 통해 그래프를 그린다. | |
compare.py | Compare | 유사도 딕셔너리 안에서 가장 유사도가 높은 사진과 유저의 사진을 출력하는 결과창. 그래프를 볼 수 있는 버튼이 포함되어 있다. |
introduction.py | Intro | 기본적인 사용설명을 적어 놓은 창. |
regist.py | Button | 버튼의 생성과 이벤트 메소드와의 연결을 한 번에 해준다. |
Register | 유저의 사진을 등록하는 기능을 가지고 있는 창. | |
StartScreen.py | ComboBox | 콤보 박스를 클릭할 때마다 자동으로 값을 업데이트 해주기 위해서 사전에 필요한 클래스. |
Button | 버튼의 생성과 이벤트 메소드와의 연결을 한 번에 해준다. | |
MainWindow | 유저 삭제 버튼, 유저 등록 버튼, 사용 설명 버튼, 결과 보기 버튼 등을 갖춘 메인 창. |
클래스 | 메소드 | 입력인자 | 출력인자 | 기능 |
---|---|---|---|---|
FaceRecognition | __init__ | self, username, usergender | None | 유저의 정보를 인자로 받아와 성별에 따라 다른 비교 데이터가 저장되어있는 디렉토리의 위치를 받아온다. 또한 이름과 일치하는 디렉토리에서 사진을 받아와 학습을 진행한다. |
face_detector | self, img | img, roi | 이미지를 받아와 얼굴 부분을 잘라낸 다음 200 x 200 크기로 맞춰 roi와 원본이미지를 출력한다. | |
compare_face | self | conf_dict | 유저의 얼굴과 유저의 성별에 맞는 연예인의 얼굴을 비교해 key는 연예인의 이름 value는 유사도로 해서 딕셔너리로 묶은 다음 출력한다. | |
draw_graph | self, table | None | 인자로 딕셔너리를 받아와 matplotlib를 이용해 그래프를 그린다. 주어진 파일 안에서 테스트하기 위해서 만들어진 함수이다. | |
make_file | self, filepath, revised_filepath | None | 유저와 가장 유사도가 높게 나온 사진을 보여줄 때 전신 사진이 아니라 얼굴 사진만을 보여주기 위해서 이미지를 가공해서 새로 이미지를 만드는 기능을 구현했다. | |
FaceCapture | face_extractor | img | cropped_face | 기능은 크게 face_detector와 다르지 않으나 capture_face를 스태틱 메소드로 사용하고 싶어서 추가한 기능이다. 출력이 face_detector와 다르게 cropped_face 하나 밖에 없다. |
capture_face | username | None | 기본 설정된 카메라를 통해 사진을 찍는다. 사진을 찍고 얼굴이라고 인지된 사진을 100장 뽑아 낼 때까지 루프를 돈다. 유저 이름을 인자로 받아와 유저이름을 갖는 디렉토리를 생성하고 그 안에 얼굴사진 100장을 저장한다. | |
Button | __init__ | self, text, callback | None | 텍스트의 이름을 갖는 버튼을 만들고 callback 함수 인자에 주어진 함수로 이벤트 메소드를 연결한다. |
BarGrapth | __init__ | self, dic | None | 유사도가 기록된 딕셔너리를 받아 self.conf_dict에 저장하고 setupUI를 호출한다. |
setupUI | self | None | Draw 버튼과 More 버튼을 생성하고 통계 창을 띄울 FigureCanvas와 데이터 리스트를 띄울 textEdit을 생성한다. | |
pushButtonClicked | self | None | 버튼이 눌리면 버튼의 이름에 따라 기능한다. Draw가 입력되면 통게를 그리고, More가 입력되면 가지고 있는 데이터를 모두 띄운다. | |
Compare | __init__ | self, username, usergender, parent | None | 유저의 이름과 성별을 받아와서 FaceRecognition 클래스에 전달한다. 정보를 표시할 레이블과 이미지를 가져오기 위한 QPixmap과 스테이터스 바와 막대그래프 버튼이 선언되어 있다. |
buttonClicked | self | None | 막대 그래프 버튼이 눌리면 그래프 창을 띄운다. 그래프 창을 띄울 때 인자로 self.conf_dict를 보내준다. | |
center | self | None | 버튼의 위치를 가운데로 조정해준다. | |
Intro | __init__ | self, parent | None | 사용설명을 위한 텍스트가 저장되어 있고 textEdit이 선언되어 있다. |
Register | __init__ | self, parent | None | 이미지를 넣기 위한 QPixmap과 정보를 담는 레이블, 성별을 결정하는 QComboBox와 이름을 입력하는 QLineEdit, 그리고 작동 버튼이 선언되어 있다. |
buttonClicked | self | None | 버튼이 눌리면 유저의 성별과 이름을 받아와 딕셔너리 형태로 가공해 user_lst에 추가해주고 같은 디렉토리 내에 있는 user_info.txt 파일에 pickle을 이용해 user_lst를 기록한다. user_lst는 클래스 외부에 선언되어 있으며 프로그램이 실행될 때 바로 파일을 읽어와 저장하게 되어있다. 만약 파일이 존재하지 않으면 빈 리스트로 주어진다. | |
center | self | None | 버튼의 위치를 가운데로 조정해준다. | |
ComboBox | showPopup | self | None | updateComb를 이용하기 위해서 사전에 해둬야 하는 설정들이 있다. |
MainWindow | __init__ | self, parent | None | 배경화면으로 지정할 이미지를 가져오고 버튼, 텍스트 입력창, 항목 선택 바를 생성한다. |
updateComb | self | None | ComboBox가 선택이 되면 자동으로 안에 있던 item들을 초기화 하고 새로 user_lst를 스캔하여 item을 등록한다. | |
center | self | None | 버튼의 위치를 가운데로 조정해준다. | |
buttonClicked | self | None | 버튼이 눌리면 버튼의 텍스트에 따라 각각 기능하는데 유저 삭제 기능은 이 함수 안에 구현되어 있다. regist.py에서 가져온 user_lst를 스캔하여 텍스트 입력창에 입력된 유저의 이름과 일치하는 유저를 삭제한다. |
FaceRecognition | 이름 | 역할, 설명 |
---|---|---|
attribute | self.username | 인자로 받아온 유저의 이름을 저장하는 변수이다. |
self.usergender | 인자로 받아온 유저의 성별을 저장하는 변수이다. | |
self.face_classifier | xml 파일에 저장되어 있는 데이터를 바탕으로 학습한 얼굴을 찾는 객체를 선언한다. | |
self.userFolderPath | 유저의 사진이 저장되어 있는 디렉토리의 주소를 저장한다. | |
self.userFiles | self.userFolderPath 주소 안에 있는 파일들의 이름을 저장하는 리스트이다. | |
self.gender_path | 유저의 성별을 바탕으로 비교할 사진이 담겨진 디렉토리의 주소를 저장한다. | |
self.otherFiles | self.gender_path 주소 안에 있는 파일들의 이름을 저장하는 리스트이다. | |
self.Tranning_Data | user 사진의 이미지 데이터를 리스트로 받아와서 리스트를 요소로 갖는 리스트이다. | |
self.Labels | user 사진에 번호를 매겨 저장하는 리스트이다. | |
self.model | self.Lables와 self.Tranning_Data를 바탕으로 학습한 모델이다. | |
methods | **init** | 변수들을 선언하고 저장한다. self.userfiles와 self.userFolderPath를 이용해 유저 사진의 주소를 구하고 데이터를 읽어와 self.Training_Data에 저장한다. |
update_data | self.userFolderPath와 self.gender_path를 다시 스캔해서 저장한다. | |
face_detector | self.face_classifier를 이용해 주어진 img에서 얼굴을 추출해 faces에 저장하고 사이즈를 200 x 200 으로 바꿔 roi에 저장해 원본파일과 함께 출력한다. | |
compare_face | self.genderPath와 self.otherFiles를 이용해 연예인 사진의 주소를 구하고 이미지를 불러온다. 그리고 face_detector를 이용해 연예인의 얼굴만 추출한 데이터를 self.model를 이용해 유저와의 유사도를 예측한다. 마지막으로 결과값을 연예인의 이름과 짝 지어 딕셔너리 형태로 출력한다. | |
make_file | 입력 주소와 출력 주소를 받아 입력 주소에서 얼굴만 찾아서 잘라낸 이미지를 출력주소에 저장한다. | |
FaceCapture | 이름 | 역할, 설명 |
attribute | \- | \- |
methods | face_extractor | 이미지를 받아와 흑백으로 전환해 얼굴을 찾고 이미지를 잘라내 출력한다. |
capture_face | 기본값으로 설정되어 있는 카메라를 통해 이미지를 입력받는다. username을 인자로 받아서 user이름으로 된 디렉토리를 만들고 그 안에 유저의 얼굴만을 잘라낸 사진들을 저장한다. |
class MainWindow | 이름 | 역할, 설명 |
---|---|---|
Attribute (properties) | background | 시작 window의 배경화면 이미지를 절대경로를 통해 바인딩한 변수. QSize를 통해 width와 height을 맞춰주었다. |
palette | 배경화면을 설정해주기 위해 QPalette를 바인딩한 변수. setBrush로 background 이미지를 받음. | |
title | "Face Recognition"이라는 문자열을 갖는 QLabel. setStyleSheet, setFont로 문자열의 색, 글꼴, 글자 사이즈, 볼드체를 설정해주었다. | |
textinput | QLineEdit을 사용하여 지울 이름을 작성하게 하였다. | |
removebutton | textinput에 적혀져 있는 텍스트에 해당하는 유저를 삭제하는 기능을 하는 버튼이다. | |
enrollmentbutton | Register window를 실행하여 사진을 찍고 유저 등록을 위한 버튼이다. | |
combobox | 등록한 유저들을 선택할 수 있는 combobox이다. | |
startbutton | combobox에 선택 된 유저의 결과를 보여주는 버튼이다. | |
introductionbutton | 사용설명서의 내용을 담고 있는Intro window를 실행시키기 위한 버튼이다. | |
removelayout | textinput Widget과 removebutton을 추가할 QHBoxLayout이다. | |
resultlayout | combobox Widget과 startbuton을 추가할 QHBoxLayout이다. | |
buttonlayout | removelayout, enrollmentbutton, resultlayout, introductionbutton을 추가할 QVBoxLayout이다. | |
vlayout | title, buttonlayout을 추가할 QVBoxLayout이다. | |
hlayout | addStrech를 통해 vlayout을 한쪽으로 몰아 넣어 줄 QHBoxLayout이다 | |
methods | **intit**() | 초기 시작 window를 화면에 띄우는 메소드이다. |
buttonClicked() | 버튼이 눌리면 버튼의 텍스트에 따라 각각의 기능을 수행하게 만들어 주는 메소드이다. | |
updateCombo | combobox 유저의 이름을 추가하는 메소드이다. | |
center | window를 화면의 중앙에 위치시키는 메소드이다. |
class Button | 이름 | 역할, 설명 |
---|---|---|
methods | **init**() | text와 callback를 인자로 받아 버튼의 텍스트를 text로 하고 callback 해당하는 내용이 버튼이 눌리면 실행되게 한다. |
sizeHint | 버튼의 width와 height를 맞춰준다. |
class ComboBox | 이름 | 역할, 설명 |
---|---|---|
Attributes (properties) | popupAboutToBeShown | pyatSingal을 바인딩한 변수이다. |
methods | showPopup | 콤보 박스를 클릭할 때마다 자동으로 값을 업데이트 해주는 메소드이다. |
class Intro | 이름 | 역할, 설명 |
---|---|---|
attribute (properties) | text | 설명이 포함 되어져 있는 문자열을 바인딩할 변수 |
introduce | Layout 에 더해줄 Widget이자 text의 내용을 담을 변수. Qt.AlignLeft로 왼쪽 정렬을 해주었다. | |
mainlayout | 화면에 표시할 window | |
methods | **intit**() | 화면에 사용설명서 창을 띄움 |
class Compare | 이름 | 역할, 설명 |
---|---|---|
Attributes (properties) | f | FaceRecognition() 클래스를 바인딩한 변수이다. |
conf_dic | f.compare_face()를 실해하여 userimage와 otherimage를 비교한 결과 값을 딩dictionary 형식으로 return 받은 값을 바인딩한 변수이다. | |
conf_rank | conf_dic의 key를 key에 따른 value를 기준으로 정렬시켜 놓은 리스트이다. | |
userimagebox | "본인 사진"이라는 문자열을 갖는 QLabel을 바인딩한 변수이다. setStyleSheet, setFont로 문자열의 색, 글꼴, 글자 사이즈, 볼드체를 설정해주었다. | |
resultimagebox | "가장 비슷한 연예인"이라는 문자열을 갖는 QLabel을 바인딩한 변수이다. setStyleSheet, setFont로 문자열의 색, 글꼴, 글자 사이즈, 볼드체를 설정해주었다. | |
userimage | QPixmap을 활용하여 절대경로를 바탕으로 userimage를 불러왔고 scaledToHeight()를 통해 높이 기준으로 이미지를 축소 시켰다. | |
userimage_label | userimage를 widget으로 변환시켜주기 위해 QLabel을 바인딩 시켜놓음. | |
vstext | "vs"이라는 문자열을 갖는 QLabel을 바인딩한 변수이다. setStyleSheet, setFont로 문자열의 색, 글꼴, 글자 사이즈, 볼드체를 설정해주었다. | |
resultimage | QPixmap을 활용하여 절대경로를 바탕으로, 닮은 비율이 가장 높은 otherimage를 불러왔고 scaledToHeight()를 통해 높이 기준으로 이미지를 축소 시켰다. | |
resultimage_label | resultimage를 widget으로 변환시켜주기 위해 QLabel을 바인딩 시켜놓음. | |
resultpercentage | QProgressBar를 활용하여 퍼센테이지를 시각화하였다. | |
leftbox | userimagebox와 userimage_label을 추가할 QVBoxLayout이다. | |
midbox | vstext를 추가할 QVBoxLayout이다. | |
rightbox | resultimagebox와 resultimage_label을 추가할 QVBoxLayout이다. | |
staticbutton | 버튼이 눌리면 결과값의 통계인 BarGraph window를 표시한다. | |
optionbox | resultpercentage와 staticbutton을 추가할 QHBoxLayout이다. | |
mainwindow | leftbox, midbox, rightbox 를 추가할 QHBoxLayout이다. | |
realmainwindow | mainwindow와 optionbox를 추가할 QVBoxLayout이다. | |
methods | **init**() | 선택된 userimage와 가장 비슷한 otherimgae를 표시해줄 window를 띄우는 메소드이다. |
buttonClicked() | 버튼이 눌리면 버튼의 텍스트에 따라 각각의 기능을 수행하게 만들어 주는 메소드이다. | |
center | window를 화면의 중앙에 위치시키는 메소드이다. |
class Register | 이름 | 역할, 설명 |
---|---|---|
Attributes (properties) | namelabel | "Name"이라는 문자열을 갖는 QLabel이다. |
search | 자신의 이름을 쓸 QLineEdit이다. | |
userimage | QPixmap을 활용하여 절대경로를 바탕으로 userimage를 불러왔고 scaledToHeight()를 통해 높이 기준으로 이미지를 축소 시켰다. 처음에는 회색 빈 화면을 띄우다가 검색 버튼이 눌리고 난 후 userimage로 변경된다. | |
userimage_label | userimage를 widget으로 변환시켜주기 위해 QLabel을 바인딩 시켜놓음. | |
progress | QProgressBar를 활용하여 퍼센테이지를 시각화하였다 | |
combo | "man", "woman" 을 선택할 combobox를 만들었다. | |
searchbutton | namelabel, combo 를 바탕으로 buttonClicked()를 실행한다. | |
rightlayout | namelabel, search, combo, searchbutton, progress를 추가해줄 QVBoxLayout이다. | |
mainlayout | userimage_label, rightlayout을 추가할 QHBoxLayout이다. | |
methods | **inint**() | 유저를 등록해줄 window를 띄운다. |
buttonClicked() | search, combo의 텍스트를 활용하여, 만약 이 값이 존재한다면 덮어씌우고 없다면 이를 dictionary로 만들어 user_lst에 append한다. 그 후 이를 "user_info.txt"에 user_lst를 저장하고 사진을 찍는다. 사진을 찍은 후 userimage를 gray에서 본인 이미지로 변환시킨다. | |
center | window를 화면의 중앙에 위치시키는 메소드이다. |
https://github.com/ehyeok9/Software-Project-II---AD-project
Test Case | UUT | Description |
---|---|---|
UT1-1 | FaceRecogniton | 핵심 알고리즘인 얼굴 인식 기능이 제대로 동작하는지 확인 |
IT1-1 | StartScreen | 시작화면부터 유저를 등록하고 검사하고 삭제하는 과정까지를 전부 테스트 |