Detección de rostros

OpenCV nos facilita la terea de detectar rostros o caras pues ya cuenta con clasificadores en cascada entrenados para esta tarea, estos son almacenados en archivos XML, en caso de que lo necesitemos podemos crear nuestros propios clasificadores para detectar el objeto para el que haya sido entrenado, por ejemplo: carros, animales, frutas, etc., en el archivo de descarga de la librería vienen incluidas varios de estos archivos y las aplicaciones necesarios para construir los nuestros.

Detección de rostros en OpenCV

Para detectar un rostro primero debemos procesar la imagen en la cual deseamos buscar un rostro, luego de cargar la imagen debemos aplicar los siguientes pasos:

Convertir la imagen a escala de grises, necesario para el correcto funcionamiento de los algoritmos de detección de caras usados por la biblioteca. Para convertir una imagen a escala de grises o a otro formato contamos con la función cvtColor la utilizamos del siguiente modo:

cvtColor(imagen, imagen, CV_BGR2GRAY);

Lo siguiente que debemos hacer es aplicar ecualización de histograma a la imagen en grises para estandarizar el contraste y brillo de la imagen, esto para que distintas condiciones de iluminación no afecten la detección del rosto en la imagen, de este modo el algoritmo es más eficaz al detectar las caras presentes en una imagen.

equalizeHist(imagen, imagen);

Con esto tendremos este resultado:

detección de rostros con opencv

Para aumentar la velocidad de detección del algoritmo podemos escalar la imagen a un tamaño más pequeño, no demasiado.

Con la imagen procesada y preparada ahora debemos cargar el detector que deseamos utilizar, pasaremos el nombre del clasificador al método load de la clase CascadeClassifier, los archivos .xml que debemos cargar se encuentran en C:\opencv\data aquí encontraremos varias carpetas que contienes distintos tipos de clasificadores, en la carpeta C:\opencv\data\haarcascades se encuentran varios clasificadores no solo para detectar rostros sino también para la detección de ojos, boca, nariz, entre otros.

Para detectar rostros de frente usaremos haarcascade_frontalface_alt.xml, para detectar cuerpo completo podemos usar haarcascade_fullbody.xml, para detectar ojos contamos con haarcascade_eye.xml, existen muchos otros.

Inicializar el detector con el archivo indicado, asumimos que el archivo se encuentra en la carpeta del proyecto.

CascadeClassifier detector;

if(!detector.load("haarcascade_frontalface_alt.xml")) 
       cout << "No se puede abrir clasificador."<< endl;

Ahora podemos detectar los rostros presentes en la imagen, las coordenadas se guardarán en la variable llamada rect.

vector<Rect> rect;
detector.detectMultiScale(dest, rect);

Recorremos los rectángulos encontrados por el algoritmo y los marcamos en la imagen original.

for(Rect rc : rect)
{
       rectangle(imagen, 
                   Point(rc.x, rc.y), 
                   Point(rc.x + rc.width, rc.y + rc.height),
                   CV_RGB(0,255,0), 2);
}

rostro detectado con opencv

Código C++ Detección de Rostros:

Detección de rostros en tiempo real

Para detectar rostros en tiempo real solo debemos leer las imágenes de la webcam y aplicarle a cada una de ellas el procedimiento descrito anteriormente, para ver cómo usar la webcam.

Código de ejemplo para detectar rostros en tiempo real mediante el uso de la cámara web OpenCV.

Parámetros de la función de detección de rostros:

detectMultiScale(const Mat& image, vector<Rect>& objects, double scaleFactor=1.1, int minNeighbors=3, int flags=0, Size minSize=Size(), Size maxSize=Size())
  • image: imagen procesada.
  • objectcs: vector donde se almacenara las coordenadas de las caras encontradas.
  • scaleFactor: factor de escala, 1.2 más rápido.
  • minNeighbors: factor para prevenir falsas detecciones.
  • flags: parámetro actualmente no es usado, indicar 0.
  • minSize, maxSize: tamaño máximo y mínimo de ventana usado para detectar rostros, limita la detección de rostros muy pequeño o demasiado grandes.

Espero les sirva de ayuda, más adelante veremos como reconocer o identificar un rostro, hasta la próxima.

Lo siguiente que debes aprender: Detector de Ojos, luego Reconocimiento Facial

Comentarios

  1. me arroja este error: error C2143: syntax error : missing ',' before ':'

    ResponderEliminar
    Respuestas
    1. Dame mas detalles del error, puede ser que uses un compilador que no admite C++ 11.

      Eliminar
    2. Es con el tema de: for(Rect rc:rect), no se que compilador ocupara visual studio 2010, podra ser por eso?

      Eliminar
    3. en que linea ? xddd puede ser que te conmiste un punto y coma justo en la linea de arriba ? xd o por el ciclo for si ...

      Eliminar
    4. tengo el mismo error ya lo pudiste solucionar?

      Eliminar
    5. //use la siguiente linea
      for(size_t i = 0; i < rect.size(); i++ )
      {

      rectangle(imagen,Point(rect[i].x, rect[i].y),Point(rect[i].x + rect[i].width, rect[i].y + rect[i].height),CV_RGB(0,255,0), 2);

      }

      Eliminar
  2. hola que librerías de open cv usas yo estoy con el 2.4.8 y me muestra las imágenes pero no con la detención de rostros, me arroja el siguiente error No se puede abrir clasificador.

    ResponderEliminar
    Respuestas
    1. Los clasificadores se encuentran en la carpeta de instalación de opencv.

      opencv\data\haarcascades

      Debes cambiar la ruta para que encuentre el clasificador o puedes copiar el clasificador en la carpeta raíz del proyecto.

      Eliminar
  3. ayuda xfavor al compilar este codoigo me sale el error range-based for loops are not allowed in c++98 mode y es debido a esta linea de comando(linea 29) " for(Rect rc : rect)" lo que leí es que este comando solo se ejecuta en c++11 ...no se que hacer si actualizar el compilador ya que estoy usando qt5.1.0 y opencv 2.4.9 ..o cambiar esa linea de comando para escribir con c++98 ...si alguien tiene una solucion xfavor ayuda

    ResponderEliminar
    Respuestas
    1. Puedes cambiar esta linea de código de este modo:
      for(int i = 0; i < rect.size(), i++) { Rect rc = rect[i];
      //......
      Reemplaza la linea #29 y la #30, si tienes dificultades me avisas.

      Eliminar
    2. si ya lo puede solucionar muchas gracias x el aporte

      Eliminar
    3. amigos me sale el mismo error me pueden ayudar a solucionarlo x favor?

      Eliminar
  4. una pregunta adicional estube revisando informacion y encontre que se puede ejecutar el codigo en forma paralela y optimizar el uso de los nucles d la pc con TBB de intel ...estoy tratando de contruir esta biblioteca con cmake ...pero dicen q debo construir primeramente con mingw32-make y la verdad ya voy algun tiempo y no e podido incluir esto a mi proyecto si saben algo de como solucionar esto x favor ayundemen ¡¡¡¡¡¡

    ResponderEliminar
  5. hola ,podrias ayudarme,porque me sale:
    OpenCV Error: Assertion failed (scn == 3 || scn == 4) in cv::cvtColor, file C:\b
    uildslave64\win64_amdocl\2_4_PackSlave-win32-vc11-shared\opencv\modules\imgproc\
    src\color.cpp, line 3737

    ResponderEliminar
  6. Hola amigos, buen aporte. Soy nuevo usando esta libreria y tratando de hacer un proyecto en QtCreator 5.3.1 el programa compila pero me arroja el siguiente error:

    QMetaType::registerType: Binary compatibility break -- Size mismatch for type 'QPaintBufferCacheEntry' [1024]. Previously registered size 0, now registering size 12.
    The program has unexpectedly finished.

    Agradeceria mucho su ayuda. Saludos

    ResponderEliminar
  7. Y pensar que yo me mate buscando el algoritmo de canny y programandolo tarde una semana :grin: y ya hay una libreria que lo hace, y bastante bien xd mañana pruebo esta libreria, la estoy bajando ...

    ResponderEliminar
  8. Buen día.

    Estuve compilando el código, pero me salen varios errores. el primero creo q tiene q ver con la inclusión de librerías. El mensaje es el siguiente:

    Description Resource Path Location Type
    referencia a `cv::CascadeClassifier::~CascadeClassifier()' sin definir TestPrj.cpp /TestPrj/src line 10 C/C++ Problem


    Me podría orientar por favor Agradezco su ayuda

    ResponderEliminar
  9. hHola , muchas GRAcias por las notas; tuve dos errores y necesito ayuda; el primero es que el comando CascadeClassifier sale como no identificado; Se que mi carpeta Data se encuentra dentro de la carpeta Sources y quiza esa sea la raxon, hice etc cosas como copiar la carpeta Data fuera, o el mismo XMl pero nada, por favor ayuda; y el sgt error es for(Rect rc : rect) ; aparece c++ 98 no permite esto , Ayuda y Bendiciones , gracias por tus aportes.

    ResponderEliminar
    Respuestas
    1. MAS ARRIBA PARECE QUE SE CORRIGE CAMBIANDO POR LAS LINEAS
      Puedes cambiar esta linea de código de este modo:
      for(int i = 0; i < rect.size(), i++) { Rect rc = rect[i];
      //......
      Reemplaza la linea #29 y la #30, si tienes dificultades me avisas.

      Eliminar
  10. hola me sale este error en code blocks.
    ||=== Build: Debug in opencv-test3 (compiler: GNU GCC Compiler) ===|
    obj\Debug\objectDetection.o||In function `main':|
    C:\Users\leo\Desktop\codeblockproyectos\opencv-test3\objectDetection.cpp|10|undefined reference to `cv::CascadeClassifier::CascadeClassifier()'|
    C:\Users\leo\Desktop\codeblockproyectos\opencv-test3\objectDetection.cpp|11|undefined reference to `cv::CascadeClassifier::load(std::string const&)'|
    C:\Users\leo\Desktop\codeblockproyectos\opencv-test3\objectDetection.cpp|27|undefined reference to `cv::CascadeClassifier::detectMultiScale(cv::Mat const&, std::vector, std::allocator > >&, double, int, int, cv::Size_, cv::Size_)'|
    C:\Users\leo\Desktop\codeblockproyectos\opencv-test3\objectDetection.cpp|43|undefined reference to `cv::CascadeClassifier::~CascadeClassifier()'|
    C:\Users\leo\Desktop\codeblockproyectos\opencv-test3\objectDetection.cpp|43|undefined reference to `cv::CascadeClassifier::~CascadeClassifier()'|
    ||=== Build failed: 5 error(s), 0 warning(s) (0 minute(s), 2 second(s)) ===|

    como lo puedo solucionar? muchas gracias..

    ResponderEliminar
    Respuestas
    1. Tienes que añadir a tus librerías opencv_objdetect249.lib (en el caso de estar usando opencv 2.4.9

      Eliminar
  11. ¿Hay alguna manera de compilar el programa en Ubuntu sin usar un IDE?

    ResponderEliminar
  12. Hola, en mi caso, me dice que no puede cargar el archivo xml, si esta la ruta correcta

    ResponderEliminar
  13. Se produjo una excepción:infracción de acceso de lectura.
    std::vector,std::allocator > >::operator[](...) devolvió 0x1F00994F000.

    En esté caso que se puede hacer ? de antemano gracias por atender mi consulta

    ResponderEliminar
  14. Buenas Tardes Estoy realizando un proyecto (aplicación en Android) en el que debo detectar personas que ingresan a un lugar, y llevar un conteo, alguien podría ayudarme si tienen un tutorial o algo que me pueda ser de ayuda

    Gracias

    ResponderEliminar

Publicar un comentario

Temas relacionados

Entradas populares de este blog

tkinter Grid

Histogramas OpenCV Python

tkinter Canvas

Modelo de Iluminación Phong - Tutorial OpenGL