Logotipo de Zephyrnet

Estimación de pose en tiempo real a partir de video en Python con YOLOv7

Fecha:

Introducción

La detección de objetos es un campo amplio en la visión por computadora y una de las aplicaciones más importantes de la visión por computadora "en la naturaleza". De él, se extrajo la detección de puntos clave (a menudo utilizada para la estimación de la pose).

Los puntos clave pueden ser varios puntos: partes de una cara, extremidades de un cuerpo, etc. La estimación de pose es un caso especial de detección de puntos clave, en el que los puntos son partes de un cuerpo humano.

La estimación de poses es un uso sorprendente, extremadamente divertido y práctico de la visión artificial. Con él, podemos eliminar el hardware utilizado para estimar poses (trajes de captura de movimiento), que son costosos y difíciles de manejar. Además, podemos mapear el movimiento de los humanos al movimiento de los robots en el espacio euclidiano, lo que permite un movimiento de motor de precisión fina sin usar controladores, que generalmente no permiten niveles más altos de precisión. La estimación de puntos clave se puede usar para traducir nuestros movimientos a modelos 3D en AR y VR, y se usa cada vez más para hacerlo solo con una cámara web. Finalmente, la estimación de la pose puede ayudarnos en los deportes y la seguridad.

En esta guía, realizaremos una estimación de pose en tiempo real a partir de un video en Python, utilizando el modelo YOLOv7 de última generación.

Específicamente, trabajaremos con un video de los Juegos Olímpicos de Invierno de 2018, que se llevaron a cabo en PyeongChang, Corea del Sur:

Aljona Savchenko y Bruno Massot realizaron una actuación increíble, que incluyó cuerpos superpuestos contra la cámara, movimientos rápidos y fluidos y giros en el aire. ¡Será una oportunidad increíble para ver cómo el modelo maneja situaciones difíciles de inferir!

Estimación de YOLO y Pose

YOLO (Solo se mira una vez) es una metodología, así como una familia de modelos construidos para la detección de objetos. Desde el inicio en 2015, YOLOv1, YOLOv2 (YOLO9000) y YOLOv3 han sido propuestos por los mismos autores, y la comunidad de aprendizaje profundo continuó con avances de código abierto en los años siguientes.

YOLOv5 de ultralíticos es un repositorio de detección de objetos de nivel industrial, construido sobre el método YOLO. Está implementado en PyTorch, a diferencia de C++ para los modelos anteriores de YOLO, es totalmente de código abierto y tiene una API maravillosamente simple y poderosa que le permite inferir, entrenar y personalizar el proyecto de manera flexible. Es un elemento tan básico que la mayoría de los nuevos intentos de mejorar el método YOLO se basan en él.

Esta es la forma YOLOR (Solo Aprendes Una Representación) ¡y YOLOv7 que se construyeron sobre YOLOR (mismo autor) también fueron creados!

YOLOv7 no es solo una arquitectura de detección de objetos: proporciona nuevos cabezales de modelo, que pueden generar puntos clave (esqueletos) y realizar segmentación de instancias además de solo regresión de cuadro delimitador, que no era estándar con los modelos YOLO anteriores. Esto no es sorprendente, ya que muchas arquitecturas de detección de objetos también se reutilizaron anteriormente para tareas de detección de puntos clave y segmentación de instancias, debido a la arquitectura general compartida, con diferentes salidas según la tarea.

Aunque no es sorprendente, es probable que admitir la segmentación de instancias y la detección de puntos clave se conviertan en el nuevo estándar para los modelos basados ​​en YOLO, que comenzaron a superar prácticamente a todos los demás detectores de dos etapas hace un par de años en términos de precisión y velocidad.

Esto hace que la segmentación de instancias y la detección de puntos clave sean más rápidas que nunca, con una arquitectura más simple que los detectores de dos etapas.

El modelo en sí se creó a través de cambios arquitectónicos, además de optimizar aspectos de la capacitación, denominados "bolsa de regalos", que aumentaron la precisión sin aumentar el costo de la inferencia.

Instalando YOLOv7

Comencemos clonando el repositorio para obtener el código fuente:

! git clone https://github.com/WongKinYiu/yolov7.git

Ahora, pasemos a la yolov7 directorio, que contiene el proyecto, y eche un vistazo a los contenidos:

%cd yolov7
!ls
/content/yolov7
cfg	   figure      output.mp4	 test.py       
data	   hubconf.py  paper		 tools
deploy	   inference   README.md	 train_aux.py
detect.py  LICENSE.md  requirements.txt  train.py
export.py  models      scripts		 utils

Nota: llamar !cd dirname lo mueve a un directorio en esa celda. Vocación %cd dirname lo mueve a un directorio a través de las próximas celdas también y lo mantiene allí.

Ahora, YOLO está destinado a ser un detector de objetos, y no se envía con pesos de estimación de pose por defecto. Querremos descargar los pesos y cargar una instancia de modelo concreto de ellos. Los pesos están disponibles en el mismo repositorio de GitHub y también se pueden descargar fácilmente a través de la CLI:

! curl -L https://github.com/WongKinYiu/yolov7/releases/download/v0.1/yolov7-w6-pose.pt -o yolov7-w6-pose.pt

 % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
100  153M  100  153M    0     0  23.4M      0  0:00:06  0:00:06 --:--:-- 32.3M

Una vez descargados, podemos importar las bibliotecas y los métodos auxiliares que usaremos:

import torch
from torchvision import transforms

from utils.datasets import letterbox
from utils.general import non_max_suppression_kpt
from utils.plots import output_to_keypoint, plot_skeleton_kpts

import matplotlib.pyplot as plt
import cv2
import numpy as np

Consulte nuestra guía práctica y práctica para aprender Git, con las mejores prácticas, los estándares aceptados por la industria y la hoja de trucos incluida. Deja de buscar en Google los comandos de Git y, de hecho, aprenden ella!

¡Excelente! Sigamos cargando el modelo y creando un script que te permita inferir poses de videos con YOLOv7 y OpenCV.

Estimación de pose en tiempo real con YOLOv7

Primero creemos un método para cargar el modelo a partir de los pesos descargados. Comprobaremos qué dispositivo tenemos disponible (CPU o GPU):

device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")

def load_model():
    model = torch.load('yolov7-w6-pose.pt', map_location=device)['model']
    
    model.float().eval()

    if torch.cuda.is_available():
        
        
        model.half().to(device)
    return model

model = load_model()

Dependiendo de si tenemos GPU o no, activaremos la precisión media (usando float16 en lugar de float32 en operaciones), lo que hace que la inferencia sea significativamente más rápida. Tenga en cuenta que se recomienda encarecidamente realizar esto en una GPU para obtener velocidades en tiempo real, ya que es probable que las CPU carezcan de la potencia para hacerlo a menos que se ejecuten en videos pequeños.

Escribamos un método de conveniencia para ejecutar la inferencia. Aceptaremos imágenes como matrices NumPy (ya que eso es lo que les pasaremos más adelante mientras leemos el video). Primero, usando el letterbox() función: cambiaremos el tamaño y rellenaremos el video a una forma con la que el modelo pueda trabajar. ¡Esto no necesita ser y no será la forma (resolución) del video resultante!

Luego, aplicaremos las transformaciones, convertiremos la imagen a media precisión (si hay una GPU disponible), la procesaremos por lotes y la ejecutaremos a través del modelo:

def run_inference(image):
    
    image = letterbox(image, 960, stride=64, auto=True)[0] 
    
    image = transforms.ToTensor()(image) 
    if torch.cuda.is_available():
      image = image.half().to(device)
    
    image = image.unsqueeze(0) 
    with torch.no_grad():
      output, _ = model(image)
    return output, image

Devolveremos las predicciones del modelo, así como la imagen como tensor. Estas son predicciones "aproximadas": contienen muchas activaciones que se superponen, y querremos "limpiarlas" usando Non-Max Supression, y trazar los esqueletos predichos sobre la imagen misma:

def draw_keypoints(output, image):
  output = non_max_suppression_kpt(output, 
                                     0.25, 
                                     0.65, 
                                     nc=model.yaml['nc'], 
                                     nkpt=model.yaml['nkpt'], 
                                     kpt_label=True)
  with torch.no_grad():
        output = output_to_keypoint(output)
  nimg = image[0].permute(1, 2, 0) * 255
  nimg = nimg.cpu().numpy().astype(np.uint8)
  nimg = cv2.cvtColor(nimg, cv2.COLOR_RGB2BGR)
  for idx in range(output.shape[0]):
      plot_skeleton_kpts(nimg, output[idx, 7:].T, 3)

  return nimg

Con esto en su lugar, nuestro flujo general se verá así:

img = read_img()
outputs, img = run_inference(img)
keypoint_img = draw_keypoints(output, img)

Para traducir eso a una configuración de video en tiempo real, usaremos OpenCV para leer un video y ejecutar este proceso para cada cuadro. En cada cuadro, también escribiremos el cuadro en un nuevo archivo, codificado como un video. Esto necesariamente ralentizará el proceso ya que estamos ejecutando la inferencia, mostrándola y escribiendo, por lo que puede acelerar la inferencia y la visualización evitando la creación de un nuevo archivo y escribiendo en él en el ciclo:

def pose_estimation_video(filename):
    cap = cv2.VideoCapture(filename)
    
    fourcc = cv2.VideoWriter_fourcc(*'MP4V')
    out = cv2.VideoWriter('ice_skating_output.mp4', fourcc, 30.0, (int(cap.get(3)), int(cap.get(4))))
    while cap.isOpened():
        (ret, frame) = cap.read()
        if ret == True:
            frame = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
            output, frame = run_inference(frame)
            frame = draw_keypoints(output, frame)
            frame = cv2.resize(frame, (int(cap.get(3)), int(cap.get(4))))
            out.write(frame)
            cv2.imshow('Pose estimation', frame)
        else:
            break

        if cv2.waitKey(10) & 0xFF == ord('q'):
            break

    cap.release()
    out.release()
    cv2.destroyAllWindows()

El VideoWriter acepta varios parámetros: el nombre del archivo de salida, el FourCC (cuatro códigos de códec, que indican el códec utilizado para codificar el video), la velocidad de fotogramas y la resolución como una tupla. Para no adivinar o cambiar el tamaño del video, hemos utilizado el ancho y la altura del video original, obtenidos a través de la VideoCapture instancia que contiene datos sobre el video en sí, como el ancho, la altura, el número total de fotogramas, etc.

Ahora, podemos llamar al método en cualquier video de entrada:

pose_estimation_video('../ice_skating.mp4')

Esto abrirá una ventana de OpenCV, mostrando la inferencia en tiempo real. Y también, escribirá un archivo de video en el yolov7 directorio (ya que hemos cd'd en él):

Nota: Si su GPU tiene problemas, o si desea integrar los resultados de un modelo como este en una aplicación que tiene la latencia como un aspecto crucial del flujo de trabajo, haga el video más pequeño y trabaje en marcos más pequeños. Este es un video Full HD 1920 × 1080, y debería poder ejecutarse rápido en la mayoría de los sistemas domésticos, pero si no funciona tan bien en su sistema, reduzca las imágenes.

Conclusión

En esta guía, hemos analizado el método YOLO, YOLOv7 y la relación entre YOLO y la detección de objetos, la estimación de poses y la segmentación de instancias. Luego, echamos un vistazo a cómo puede instalar y trabajar fácilmente con YOLOv7 usando la API programática, y creamos varios métodos convenientes para facilitar la inferencia y la visualización de resultados.

Finalmente, abrimos un video usando OpenCV, ejecutamos la inferencia con YOLOv7 y creamos una función para realizar la estimación de poses en tiempo real, guardando el video resultante en resolución completa y 30FPS en su disco local.

Yendo más lejos: aprendizaje profundo práctico para la visión por computadora

¿Tu naturaleza inquisitiva te hace querer ir más allá? Recomendamos revisar nuestro Curso: “Aprendizaje Profundo Práctico para Visión por Computador con Python”.

¿Otro curso de visión artificial?

No haremos clasificación de dígitos MNIST o moda MNIST. Cumplieron su parte hace mucho tiempo. Demasiados recursos de aprendizaje se centran en conjuntos de datos básicos y arquitecturas básicas antes de permitir que las arquitecturas avanzadas de caja negra carguen con la carga del rendimiento.

queremos centrarnos en desmitificación, sentido práctico, comprensión, intuición y proyectos reales. Querer aprender cómo ¿Tu puedes hacer la diferencia? Lo llevaremos en un viaje desde la forma en que nuestros cerebros procesan imágenes hasta escribir un clasificador de aprendizaje profundo de grado de investigación para el cáncer de mama y redes de aprendizaje profundo que "alucinan", enseñándole los principios y la teoría a través del trabajo práctico, equipándolo con el conocimientos y herramientas para convertirse en un experto en la aplicación del aprendizaje profundo para resolver la visión artificial.

¿Qué hay adentro?

  • Los primeros principios de la visión y cómo se puede enseñar a las computadoras a “ver”
  • Diferentes tareas y aplicaciones de la visión artificial
  • Las herramientas del oficio que facilitarán tu trabajo
  • Encontrar, crear y utilizar conjuntos de datos para la visión por computadora
  • La teoría y aplicación de las Redes Neuronales Convolucionales
  • Manejo de cambio de dominio, co-ocurrencia y otros sesgos en conjuntos de datos
  • Transfiera el aprendizaje y utilice el tiempo de capacitación y los recursos computacionales de otros para su beneficio
  • Construyendo y entrenando un clasificador de cáncer de mama de última generación
  • Cómo aplicar una buena dosis de escepticismo a las ideas principales y comprender las implicaciones de las técnicas ampliamente adoptadas
  • Visualización del "espacio conceptual" de ConvNet usando t-SNE y PCA
  • Casos prácticos de cómo las empresas utilizan técnicas de visión artificial para lograr mejores resultados
  • Evaluación adecuada del modelo, visualización del espacio latente e identificación de la atención del modelo.
  • Realizar investigaciones de dominio, procesar sus propios conjuntos de datos y establecer pruebas modelo
  • Arquitecturas de vanguardia, la progresión de las ideas, qué las hace únicas y cómo implementarlas
  • KerasCV: una biblioteca WIP para crear canalizaciones y modelos de última generación
  • Cómo analizar y leer documentos e implementarlos usted mismo
  • Selección de modelos en función de su aplicación
  • Creación de una canalización de aprendizaje automático de extremo a extremo
  • Panorama e intuición sobre la detección de objetos con Faster R-CNN, RetinaNets, SSD y YOLO
  • Instancia y segmentación semántica
  • Reconocimiento de objetos en tiempo real con YOLOv5
  • Capacitación de detectores de objetos YOLOv5
  • Trabajando con Transformers usando KerasNLP (biblioteca WIP de fuerza industrial)
  • Integrando Transformers con ConvNets para generar subtítulos de imágenes
  • sueño profundo
  • Optimización del modelo de Deep Learning para visión artificial
punto_img

Información más reciente

punto_img