In this blog post, I will explain how to build a face detection algorithm with the machine learning components in OpenCV. We will use OpenCV to read an image from a camera and detect faces in it. The result will look like this.

Image for post

Beethoven looking grim

You can find all code for this blog post on my github.

Installing OpenCV

We will use some rather new parts of OpenCV and its OpenCV_contrib module. The most convenient way to make sure you have access to these modules is by building OpenCV from source. I used OpenCV version 4.2.0 on Ubuntu 16.04. For your convenience, I included a bash script that takes care of installing the correct OpenCV version. It will also install all necessary dependencies. The script lies in the accompanying GitHub repo.

The cv::dnn::Net class we will be using was added to OpenCV in version 3.4.10, so earlier versions might also work. But, I did not test this.

CMake setup

We will build our code with CMake. For this, we create a CMake project with a single executable and set the C++ standard to 14.

cmake_minimum_required(VERSION 3.0) 
project(OpenCVFaceDetector LANGUAGES CXX)  

add_executable(${PROJECT_NAME} main.cpp) target_compile_features(${PROJECT_NAME} PUBLIC cxx_std_14) target_include_directories(${PROJECT_NAME} PRIVATE include)

Then we take care of the OpenCV dependency. We find the OpenCV package and link our executable against it.

## OpenCV setup 
find_package(OpenCV REQUIRED) 
target_link_libraries(${PROJECT_NAME} ${OpenCV_LIBS})

The whole CMakeLists.txt file should look like this.

cmake_minimum_required(VERSION 3.0) 
project(OpenCVFaceDetector LANGUAGES CXX)  
add_executable(${PROJECT_NAME} main.cpp) target_compile_features(${PROJECT_NAME} PUBLIC cxx_std_14) target_include_directories(${PROJECT_NAME} PRIVATE include)  

## OpenCV setup find_package(OpenCV REQUIRED) target_link_libraries(${PROJECT_NAME} ${OpenCV_LIBS})

Getting an image from the camera

The first thing we have to do is getting a camera image to work with. Luckily, the cv::videocapture class makes this easy.

We include the OpenCV header to have access to OpenCV’s functionality. Next, we create a cv::videocapture object and try to open the first camera we can find.

#include <opencv4/opencv2/opencv.hpp>  
int main(int argc, char **argv) {
      cv::VideoCapture video_capture;
     if (!video_capture.open(0)) {
         return 0;
     }

Afterwards, we create a cv::Mat to hold the frame and display it in an infinite loop. If the user presses ‘Esc’ we break the loop, destroy the display window and release the video capture.

cv::Mat frame;
    while (true) {
        video_capture >> frame;

        imshow("Image", frame);
        const int esc_key = 27;
        if (cv::waitKey(10) == esc_key) { 
            break;
        }
    }

    cv::destroyAllWindows();
    video_capture.release();

    return 0;
}

So far the main.cpp file will look like the following.

#include <opencv4/opencv2/opencv.hpp>  
int main(int argc, char **argv) {
      cv::VideoCapture video_capture;
     if (!video_capture.open(0)) {
         return 0;
     }
     cv::Mat frame;
     while (true) {
         video_capture >> frame;
         imshow("Image", frame);
         const int esc_key = 27;
         if (cv::waitKey(10) == esc_key) {
              break;
         }
     }
     cv::destroyAllWindows();
     video_capture.release();
     return 0;
 }

We can now display images captured from the camera.

Image for post

#opencv #neural-networks #cpp #machine-learning #c++ #cplusplus

Building a face detector with OpenCV in C++
1.20 GEEK