initial commit
This commit is contained in:
commit
25ebd7a387
35
.gitignore
vendored
Normal file
35
.gitignore
vendored
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
# Prerequisites
|
||||||
|
*.d
|
||||||
|
|
||||||
|
# Compiled Object files
|
||||||
|
*.slo
|
||||||
|
*.lo
|
||||||
|
*.o
|
||||||
|
*.obj
|
||||||
|
|
||||||
|
# Precompiled Headers
|
||||||
|
*.gch
|
||||||
|
*.pch
|
||||||
|
|
||||||
|
# Compiled Dynamic libraries
|
||||||
|
*.so
|
||||||
|
*.dylib
|
||||||
|
*.dll
|
||||||
|
|
||||||
|
# Fortran module files
|
||||||
|
*.mod
|
||||||
|
*.smod
|
||||||
|
|
||||||
|
# Compiled Static libraries
|
||||||
|
*.lai
|
||||||
|
*.la
|
||||||
|
*.a
|
||||||
|
*.lib
|
||||||
|
|
||||||
|
# Executables
|
||||||
|
*.exe
|
||||||
|
*.out
|
||||||
|
*.app
|
||||||
|
fc2d
|
||||||
|
|
||||||
|
build/
|
14
CMakeLists.txt
Normal file
14
CMakeLists.txt
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
cmake_minimum_required( VERSION 3.0 )
|
||||||
|
project( FaceCam2D VERSION 0.1.0 )
|
||||||
|
find_package( OpenCV REQUIRED )
|
||||||
|
find_package( VTK REQUIRED )
|
||||||
|
find_package( HDF5 REQUIRED )
|
||||||
|
find_package( GLEW REQUIRED )
|
||||||
|
find_package( OpenGL REQUIRED )
|
||||||
|
find_package( glm REQUIRED )
|
||||||
|
find_package( FreeGLUT REQUIRED )
|
||||||
|
include_directories( ${OpenCV_INCLUDE_DIRS} )
|
||||||
|
include_directories( ${PROJECT_SOURCE_DIR}/src )
|
||||||
|
add_executable( fc2d src/main.cpp src/graphics.cpp )
|
||||||
|
target_link_libraries( fc2d ${OpenCV_LIBS} -lOpenGL -lglut -lGLEW )
|
||||||
|
set( CMAKE_BUILD_TYPE Debug )
|
197
Makefile
Normal file
197
Makefile
Normal file
|
@ -0,0 +1,197 @@
|
||||||
|
# CMAKE generated file: DO NOT EDIT!
|
||||||
|
# Generated by "Unix Makefiles" Generator, CMake Version 3.19
|
||||||
|
|
||||||
|
# Default target executed when no arguments are given to make.
|
||||||
|
default_target: all
|
||||||
|
|
||||||
|
.PHONY : default_target
|
||||||
|
|
||||||
|
# Allow only one "make -f Makefile2" at a time, but pass parallelism.
|
||||||
|
.NOTPARALLEL:
|
||||||
|
|
||||||
|
|
||||||
|
#=============================================================================
|
||||||
|
# Special targets provided by cmake.
|
||||||
|
|
||||||
|
# Disable implicit rules so canonical targets will work.
|
||||||
|
.SUFFIXES:
|
||||||
|
|
||||||
|
|
||||||
|
# Disable VCS-based implicit rules.
|
||||||
|
% : %,v
|
||||||
|
|
||||||
|
|
||||||
|
# Disable VCS-based implicit rules.
|
||||||
|
% : RCS/%
|
||||||
|
|
||||||
|
|
||||||
|
# Disable VCS-based implicit rules.
|
||||||
|
% : RCS/%,v
|
||||||
|
|
||||||
|
|
||||||
|
# Disable VCS-based implicit rules.
|
||||||
|
% : SCCS/s.%
|
||||||
|
|
||||||
|
|
||||||
|
# Disable VCS-based implicit rules.
|
||||||
|
% : s.%
|
||||||
|
|
||||||
|
|
||||||
|
.SUFFIXES: .hpux_make_needs_suffix_list
|
||||||
|
|
||||||
|
|
||||||
|
# Command-line flag to silence nested $(MAKE).
|
||||||
|
$(VERBOSE)MAKESILENT = -s
|
||||||
|
|
||||||
|
#Suppress display of executed commands.
|
||||||
|
$(VERBOSE).SILENT:
|
||||||
|
|
||||||
|
# A target that is always out of date.
|
||||||
|
cmake_force:
|
||||||
|
|
||||||
|
.PHONY : cmake_force
|
||||||
|
|
||||||
|
#=============================================================================
|
||||||
|
# Set environment variables for the build.
|
||||||
|
|
||||||
|
# The shell in which to execute make rules.
|
||||||
|
SHELL = /bin/sh
|
||||||
|
|
||||||
|
# The CMake executable.
|
||||||
|
CMAKE_COMMAND = /usr/bin/cmake
|
||||||
|
|
||||||
|
# The command to remove a file.
|
||||||
|
RM = /usr/bin/cmake -E rm -f
|
||||||
|
|
||||||
|
# Escaping for special characters.
|
||||||
|
EQUALS = =
|
||||||
|
|
||||||
|
# The top-level source directory on which CMake was run.
|
||||||
|
CMAKE_SOURCE_DIR = /home/rubi/repos/facecam2d
|
||||||
|
|
||||||
|
# The top-level build directory on which CMake was run.
|
||||||
|
CMAKE_BINARY_DIR = /home/rubi/repos/facecam2d
|
||||||
|
|
||||||
|
#=============================================================================
|
||||||
|
# Targets provided globally by CMake.
|
||||||
|
|
||||||
|
# Special rule for the target rebuild_cache
|
||||||
|
rebuild_cache:
|
||||||
|
@$(CMAKE_COMMAND) -E cmake_echo_color --switch=$(COLOR) --cyan "Running CMake to regenerate build system..."
|
||||||
|
/usr/bin/cmake --regenerate-during-build -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
|
||||||
|
.PHONY : rebuild_cache
|
||||||
|
|
||||||
|
# Special rule for the target rebuild_cache
|
||||||
|
rebuild_cache/fast: rebuild_cache
|
||||||
|
|
||||||
|
.PHONY : rebuild_cache/fast
|
||||||
|
|
||||||
|
# Special rule for the target edit_cache
|
||||||
|
edit_cache:
|
||||||
|
@$(CMAKE_COMMAND) -E cmake_echo_color --switch=$(COLOR) --cyan "Running CMake cache editor..."
|
||||||
|
/usr/bin/ccmake -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
|
||||||
|
.PHONY : edit_cache
|
||||||
|
|
||||||
|
# Special rule for the target edit_cache
|
||||||
|
edit_cache/fast: edit_cache
|
||||||
|
|
||||||
|
.PHONY : edit_cache/fast
|
||||||
|
|
||||||
|
# The main all target
|
||||||
|
all: cmake_check_build_system
|
||||||
|
$(CMAKE_COMMAND) -E cmake_progress_start /home/rubi/repos/facecam2d/CMakeFiles /home/rubi/repos/facecam2d//CMakeFiles/progress.marks
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 all
|
||||||
|
$(CMAKE_COMMAND) -E cmake_progress_start /home/rubi/repos/facecam2d/CMakeFiles 0
|
||||||
|
.PHONY : all
|
||||||
|
|
||||||
|
# The main clean target
|
||||||
|
clean:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 clean
|
||||||
|
.PHONY : clean
|
||||||
|
|
||||||
|
# The main clean target
|
||||||
|
clean/fast: clean
|
||||||
|
|
||||||
|
.PHONY : clean/fast
|
||||||
|
|
||||||
|
# Prepare targets for installation.
|
||||||
|
preinstall: all
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 preinstall
|
||||||
|
.PHONY : preinstall
|
||||||
|
|
||||||
|
# Prepare targets for installation.
|
||||||
|
preinstall/fast:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 preinstall
|
||||||
|
.PHONY : preinstall/fast
|
||||||
|
|
||||||
|
# clear depends
|
||||||
|
depend:
|
||||||
|
$(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 1
|
||||||
|
.PHONY : depend
|
||||||
|
|
||||||
|
#=============================================================================
|
||||||
|
# Target rules for targets named fc2d
|
||||||
|
|
||||||
|
# Build rule for target.
|
||||||
|
fc2d: cmake_check_build_system
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 fc2d
|
||||||
|
.PHONY : fc2d
|
||||||
|
|
||||||
|
# fast build rule for target.
|
||||||
|
fc2d/fast:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/fc2d.dir/build.make CMakeFiles/fc2d.dir/build
|
||||||
|
.PHONY : fc2d/fast
|
||||||
|
|
||||||
|
src/main.o: src/main.cpp.o
|
||||||
|
|
||||||
|
.PHONY : src/main.o
|
||||||
|
|
||||||
|
# target to build an object file
|
||||||
|
src/main.cpp.o:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/fc2d.dir/build.make CMakeFiles/fc2d.dir/src/main.cpp.o
|
||||||
|
.PHONY : src/main.cpp.o
|
||||||
|
|
||||||
|
src/main.i: src/main.cpp.i
|
||||||
|
|
||||||
|
.PHONY : src/main.i
|
||||||
|
|
||||||
|
# target to preprocess a source file
|
||||||
|
src/main.cpp.i:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/fc2d.dir/build.make CMakeFiles/fc2d.dir/src/main.cpp.i
|
||||||
|
.PHONY : src/main.cpp.i
|
||||||
|
|
||||||
|
src/main.s: src/main.cpp.s
|
||||||
|
|
||||||
|
.PHONY : src/main.s
|
||||||
|
|
||||||
|
# target to generate assembly for a file
|
||||||
|
src/main.cpp.s:
|
||||||
|
$(MAKE) $(MAKESILENT) -f CMakeFiles/fc2d.dir/build.make CMakeFiles/fc2d.dir/src/main.cpp.s
|
||||||
|
.PHONY : src/main.cpp.s
|
||||||
|
|
||||||
|
# Help Target
|
||||||
|
help:
|
||||||
|
@echo "The following are some of the valid targets for this Makefile:"
|
||||||
|
@echo "... all (the default if no target is provided)"
|
||||||
|
@echo "... clean"
|
||||||
|
@echo "... depend"
|
||||||
|
@echo "... edit_cache"
|
||||||
|
@echo "... rebuild_cache"
|
||||||
|
@echo "... fc2d"
|
||||||
|
@echo "... src/main.o"
|
||||||
|
@echo "... src/main.i"
|
||||||
|
@echo "... src/main.s"
|
||||||
|
.PHONY : help
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#=============================================================================
|
||||||
|
# Special targets to cleanup operation of make.
|
||||||
|
|
||||||
|
# Special rule to run CMake to check the build system integrity.
|
||||||
|
# No rule that depends on this can have commands that come from listfiles
|
||||||
|
# because they might be regenerated.
|
||||||
|
cmake_check_build_system:
|
||||||
|
$(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 0
|
||||||
|
.PHONY : cmake_check_build_system
|
||||||
|
|
20719
haarcascade_frontalface_alt2.xml
Normal file
20719
haarcascade_frontalface_alt2.xml
Normal file
File diff suppressed because it is too large
Load diff
BIN
head-base.png
Normal file
BIN
head-base.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 19 KiB |
BIN
head-face.png
Normal file
BIN
head-face.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 9.5 KiB |
805185
lbfmodel.yaml
Normal file
805185
lbfmodel.yaml
Normal file
File diff suppressed because it is too large
Load diff
1469
lbpcascade_frontalface_improved.xml
Normal file
1469
lbpcascade_frontalface_improved.xml
Normal file
File diff suppressed because it is too large
Load diff
171
src/graphics.cpp
Normal file
171
src/graphics.cpp
Normal file
|
@ -0,0 +1,171 @@
|
||||||
|
#include <GL/glew.h>
|
||||||
|
#include <GL/freeglut.h> //includes glu.h and gl.h
|
||||||
|
#include <glm/mat4x4.hpp>
|
||||||
|
#include <glm/ext/matrix_transform.hpp>
|
||||||
|
#include <glm/gtc/type_ptr.hpp>
|
||||||
|
|
||||||
|
#define STB_IMAGE_IMPLEMENTATION
|
||||||
|
#include <stb_image.h>
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
#include <graphics.hpp>
|
||||||
|
|
||||||
|
GLuint vbo; //vertex buffer
|
||||||
|
GLuint ebo; //element buffer
|
||||||
|
GLuint vao; //vertex array (holds shader relations etc to vertex buffer)
|
||||||
|
|
||||||
|
GLuint shader; //standard shader program used for all elements
|
||||||
|
GLuint transUniform; //location of the "transMatrix" transformation matrix uniform in the shader
|
||||||
|
|
||||||
|
void display () {
|
||||||
|
glClear(GL_COLOR_BUFFER_BIT);
|
||||||
|
|
||||||
|
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);
|
||||||
|
|
||||||
|
glutSwapBuffers();
|
||||||
|
}
|
||||||
|
|
||||||
|
void initBuffers () {
|
||||||
|
glewInit();
|
||||||
|
|
||||||
|
//TODO: put quad stuff in header file or something
|
||||||
|
GLfloat quad[] = {
|
||||||
|
//vertex UV/texcoord
|
||||||
|
0.5f, 0.5f, 1.0f, 0.0f,
|
||||||
|
0.5f, -0.5f, 1.0f, 1.0f,
|
||||||
|
-0.5f, -0.5f, 0.0f, 1.0f,
|
||||||
|
-0.5f, 0.5f, 0.0f, 0.0f,
|
||||||
|
};
|
||||||
|
|
||||||
|
GLuint quadElements[] = {
|
||||||
|
0, 1, 2,
|
||||||
|
2, 3, 0
|
||||||
|
};
|
||||||
|
|
||||||
|
const char* vsSrc =
|
||||||
|
"#version 150\n"
|
||||||
|
"in vec2 position;"
|
||||||
|
"in vec2 texcoord;"
|
||||||
|
"out vec2 uv;"
|
||||||
|
"uniform mat4 transMatrix;"
|
||||||
|
"void main () {"
|
||||||
|
"gl_Position = transMatrix * vec4(position, 0.0, 1.0);"
|
||||||
|
"uv = texcoord;"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
const char* fsSrc =
|
||||||
|
"#version 150\n"
|
||||||
|
"in vec2 uv;"
|
||||||
|
"out vec4 color;"
|
||||||
|
"uniform sampler2D tex;"
|
||||||
|
"void main () {"
|
||||||
|
"color = texture(tex, uv);"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
glGenVertexArrays(1, &vao);
|
||||||
|
glBindVertexArray(vao);
|
||||||
|
|
||||||
|
glGenBuffers(1, &vbo);
|
||||||
|
glBindBuffer(GL_ARRAY_BUFFER, vbo);
|
||||||
|
//change to GL_DYNAMIC_DRAW when using deformable meshes
|
||||||
|
glBufferData(GL_ARRAY_BUFFER, sizeof(quad), quad, GL_STATIC_DRAW);
|
||||||
|
|
||||||
|
glGenBuffers(1, &ebo);
|
||||||
|
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ebo);
|
||||||
|
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(quadElements), quadElements, GL_STATIC_DRAW);
|
||||||
|
|
||||||
|
//compile vert shader
|
||||||
|
GLuint vs = glCreateShader(GL_VERTEX_SHADER);
|
||||||
|
glShaderSource(vs, 1, &vsSrc, NULL);
|
||||||
|
glCompileShader(vs);
|
||||||
|
GLint status;
|
||||||
|
glGetShaderiv(vs, GL_COMPILE_STATUS, &status);
|
||||||
|
if (status != GL_TRUE) { std::cout << "vertex shader borked" << std::endl;
|
||||||
|
printShaderCompileLog(vs); }
|
||||||
|
|
||||||
|
//compile frag shader
|
||||||
|
GLuint fs = glCreateShader(GL_FRAGMENT_SHADER);
|
||||||
|
glShaderSource(fs, 1, &fsSrc, NULL);
|
||||||
|
glCompileShader(fs);
|
||||||
|
glGetShaderiv(fs, GL_COMPILE_STATUS, &status);
|
||||||
|
if (status != GL_TRUE) { std::cout << "fragment shader borked" << std::endl;
|
||||||
|
printShaderCompileLog(vs); }
|
||||||
|
|
||||||
|
|
||||||
|
//link shaders into a shader program
|
||||||
|
shader = glCreateProgram();
|
||||||
|
glAttachShader(shader, vs);
|
||||||
|
glAttachShader(shader, fs);
|
||||||
|
glBindFragDataLocation(shader, 0, "color");
|
||||||
|
glLinkProgram(shader);
|
||||||
|
glUseProgram(shader);
|
||||||
|
|
||||||
|
|
||||||
|
//tell OpenGL what to put in the input vars
|
||||||
|
GLuint posAttr = glGetAttribLocation(shader, "position");
|
||||||
|
glVertexAttribPointer(posAttr, 2, GL_FLOAT, GL_FALSE, 4*sizeof(GLfloat), 0);
|
||||||
|
glEnableVertexAttribArray(posAttr);
|
||||||
|
GLuint uvAttr = glGetAttribLocation(shader, "texcoord");
|
||||||
|
glVertexAttribPointer(uvAttr, 2, GL_FLOAT, GL_FALSE, 4*sizeof(GLfloat), (void*)(2*sizeof(GLfloat)));
|
||||||
|
glEnableVertexAttribArray(uvAttr);
|
||||||
|
|
||||||
|
transUniform = glGetUniformLocation(shader, "transMatrix");
|
||||||
|
glUniformMatrix4fv(transUniform, 1, GL_FALSE, glm::value_ptr(glm::mat4(1.0f)));
|
||||||
|
|
||||||
|
GLuint tex;
|
||||||
|
glGenTextures(1, &tex);
|
||||||
|
glBindTexture(GL_TEXTURE_2D, tex);
|
||||||
|
|
||||||
|
int x, y, channels;
|
||||||
|
GLubyte* pixels = stbi_load("face.png", &x, &y, &channels, 4);
|
||||||
|
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, x, y, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
|
||||||
|
|
||||||
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||||
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||||
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||||
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||||
|
|
||||||
|
//enable blending for alpha textures
|
||||||
|
glEnable(GL_BLEND);
|
||||||
|
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||||
|
}
|
||||||
|
|
||||||
|
void initGraphics () {
|
||||||
|
int argc = 1;
|
||||||
|
char *argv[1] = {(char*)"fc2d"};
|
||||||
|
|
||||||
|
glutInit(&argc, argv);
|
||||||
|
glutCreateWindow("FaceCam2D");
|
||||||
|
glutInitWindowSize(512, 512);
|
||||||
|
glutDisplayFunc(display);
|
||||||
|
|
||||||
|
initBuffers();
|
||||||
|
|
||||||
|
glClearColor(0.5f, 0.5f, 0.5f, 1.0f);
|
||||||
|
}
|
||||||
|
|
||||||
|
void graphicsFrame () {
|
||||||
|
glutMainLoopEvent();
|
||||||
|
}
|
||||||
|
|
||||||
|
void printShaderCompileLog(GLuint shader) {
|
||||||
|
char logBuffer[1024];
|
||||||
|
glGetShaderInfoLog(shader, 1024, NULL, logBuffer);
|
||||||
|
std::cout << "Compile log for shader " << shader << std::endl;
|
||||||
|
std::cout << logBuffer << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
void initModel () {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void updateModel(glm::vec2 headPos) {
|
||||||
|
//calculate transform
|
||||||
|
glm::mat4 transMatrix = glm::translate(glm::mat4(1.0f), glm::vec3(headPos.x, headPos.y, 0.0f));
|
||||||
|
|
||||||
|
//upload to GPU and put in transMatrix uniform var in shader program
|
||||||
|
glUniformMatrix4fv(transUniform, 1, GL_FALSE, glm::value_ptr(transMatrix));
|
||||||
|
|
||||||
|
glutPostRedisplay();
|
||||||
|
}
|
15
src/graphics.hpp
Normal file
15
src/graphics.hpp
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
#ifndef GRAPHICS_H
|
||||||
|
#define GRAPHICS_H
|
||||||
|
|
||||||
|
#include <GL/gl.h>
|
||||||
|
#include <glm/vec2.hpp>
|
||||||
|
|
||||||
|
void initGraphics ();
|
||||||
|
|
||||||
|
void graphicsFrame ();
|
||||||
|
|
||||||
|
void printShaderCompileLog(GLuint shader);
|
||||||
|
|
||||||
|
void updateModel(glm::vec2 headPos);
|
||||||
|
|
||||||
|
#endif
|
61
src/main.cpp
Normal file
61
src/main.cpp
Normal file
|
@ -0,0 +1,61 @@
|
||||||
|
#include <opencv2/opencv.hpp>
|
||||||
|
#include <opencv2/face.hpp>
|
||||||
|
|
||||||
|
#include <graphics.hpp>
|
||||||
|
|
||||||
|
int main () {
|
||||||
|
initGraphics();
|
||||||
|
|
||||||
|
cv::CascadeClassifier faceDetector ("haarcascade_frontalface_alt2.xml");
|
||||||
|
|
||||||
|
cv::Ptr<cv::face::Facemark> facemark = cv::face::FacemarkLBF::create();
|
||||||
|
facemark->loadModel ("lbfmodel.yaml");
|
||||||
|
|
||||||
|
cv::VideoCapture vid (0);
|
||||||
|
|
||||||
|
cv::Mat frame, gray, small;
|
||||||
|
|
||||||
|
while (vid.read(frame)) {
|
||||||
|
cv::cvtColor (frame, gray, cv::COLOR_BGR2GRAY);
|
||||||
|
//downsample image for face detection, works too slow on full res
|
||||||
|
cv::pyrDown (gray, small);
|
||||||
|
cv::pyrDown (small, small);
|
||||||
|
|
||||||
|
std::vector<cv::Rect> faces;
|
||||||
|
faceDetector.detectMultiScale(small, faces);
|
||||||
|
|
||||||
|
//get biggest face
|
||||||
|
int biggestFace = 0;
|
||||||
|
int biggestArea = 0;
|
||||||
|
for (int i = 0; i < faces.size(); i++) {
|
||||||
|
//convert face region to full res, because we perform facemark on full res
|
||||||
|
faces[i] = cv::Rect (faces[i].x * 4, faces[i].y * 4, faces[i].width * 4, faces[i].height * 4);
|
||||||
|
|
||||||
|
int iArea = faces[i].area();
|
||||||
|
if (iArea > biggestArea) {
|
||||||
|
biggestFace = i;
|
||||||
|
biggestArea = iArea;
|
||||||
|
}
|
||||||
|
|
||||||
|
cv::rectangle (frame, faces[i], cv::Scalar (255, 255, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<std::vector<cv::Point2f>> landmarks;
|
||||||
|
|
||||||
|
if (facemark->fit (frame, faces, landmarks)) {
|
||||||
|
for (int i = 0; i < landmarks[biggestFace].size(); i++) {
|
||||||
|
cv::circle (frame, landmarks[biggestFace][i], 2, cv::Scalar (255, 255, 255));
|
||||||
|
}
|
||||||
|
//send control information to graphics
|
||||||
|
updateModel(glm::vec2(
|
||||||
|
((faces[biggestFace].x + (faces[biggestFace].width / 2)) * 2) / (float)frame.cols - 1,
|
||||||
|
((faces[biggestFace].y + (faces[biggestFace].height / 2)) * 2) / -(float)frame.rows + 1
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
graphicsFrame ();
|
||||||
|
|
||||||
|
cv::imshow ("Video Input", frame);
|
||||||
|
cv::waitKey (33);
|
||||||
|
}
|
||||||
|
}
|
7762
src/stb_image.h
Normal file
7762
src/stb_image.h
Normal file
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue