Hoy vamos a utilizar esta técnica para ayudarnos a calcular el tamaño de los objetos en una imagen. ¡Asegúrate de leer la publicación completa para ver cómo se hace!
Medir el tamaño de los objetos en una imagen es similar a calcular la distancia desde nuestra cámara a un objeto: en ambos casos, necesitamos definir una proporción que mida el número de píxeles por una métrica determinada.
A esto lo llamo la proporción de "píxeles por métrica", que he definido más formalmente en la siguiente sección.
La relación “píxeles por métrica” (The “pixels per metric” ratio)
Para determinar el tamaño de un objeto en una imagen, primero debemos realizar una "calibración" (que no debe confundirse con la calibración intrínseca / extrínseca) utilizando un objeto de referencia. Nuestro objeto de referencia debe tener dos propiedades importantes:
Medir el tamaño de los objetos en una imagen es similar a calcular la distancia desde nuestra cámara a un objeto: en ambos casos, necesitamos definir una proporción que mida el número de píxeles por una métrica determinada.
A esto lo llamo la proporción de "píxeles por métrica", que he definido más formalmente en la siguiente sección.
La relación “píxeles por métrica” (The “pixels per metric” ratio)
Para determinar el tamaño de un objeto en una imagen, primero debemos realizar una "calibración" (que no debe confundirse con la calibración intrínseca / extrínseca) utilizando un objeto de referencia. Nuestro objeto de referencia debe tener dos propiedades importantes:
- Propiedad # 1: Debemos conocer las dimensiones de este objeto (en términos de ancho o altura) en una unidad medible (como milímetros, pulgadas, etc.).
- Propiedad # 2: Deberíamos poder encontrar fácilmente este objeto de referencia en una imagen, ya sea en base a la ubicación del objeto (como el objeto de referencia que siempre se coloca en la esquina superior izquierda de una imagen) o por medio de apariencias (como siendo un color o forma distintivo, único y diferente de todos los demás objetos en la imagen). En cualquier caso, nuestra referencia debe ser identificable de alguna manera.
En este ejemplo, usaremos el barrio de los Estados Unidos como nuestro objeto de referencia y en todos los ejemplos, nos aseguraremos de que sea siempre el objeto más a la izquierda de nuestra imagen:
Al garantizar que el cuarto es el objeto más a la izquierda, podemos ordenar nuestros contornos de objetos de izquierda a derecha, tomar el cuarto (la moneda) (que siempre será el primer contorno en la lista ordenada) y usarlo para definir nuestros pixels_per_metric, que nosotros definimos como:
** En este caso usare la arandela como referencia, cuyo diametro es de 24mm o 0.98pulgadas/inches
pixels_per_metric = object_width / know_width
Un cuarto de los Estados Unidos tiene un ancho conocido de 0.955 pulgadas. Ahora, supongamos que nuestro object_width (medido en píxeles) se calcula con 150 píxeles de ancho (según su caja de límite asociada).
El pixels_per_metric es por lo tanto:
pixels_per_metric = 150px / 0.955in = 157px
Medición del tamaño de objetos con visión por ordenador.
Ahora que entendemos la proporción de "píxeles por métrica", podemos implementar la secuencia de comandos del controlador Python que se usa para medir el tamaño de los objetos en una imagen.
Abra un nuevo archivo, asígnele el nombre object_size.py e inserte el siguiente código:
Las líneas 2-8 importan nuestros paquetes Python requeridos. En este ejemplo, haremos un uso intensivo del paquete imutils, por lo que si no lo tiene instalado, asegúrese de instalarlo antes de continuar:
Las líneas 10 y 11 definen un método auxiliar llamado punto medio, que como su nombre indica, se usa para calcular el punto medio entre dos conjuntos de coordenadas (x, y).
Luego analizamos nuestros argumentos de línea de comando en las Líneas 14-19. Requerimos dos argumentos, --imagen, que es la ruta a nuestra imagen de entrada que contiene los objetos que queremos medir, y --width, que es el ancho (en pulgadas) de nuestro objeto de referencia, que se presume que es el más a la izquierda. Objeto en nuestra imagen.
Ahora podemos cargar nuestra imagen y preprocesarla:
Las líneas 22-24 cargan nuestra imagen desde el disco, la convierten a escala de grises y luego la suavizan utilizando un filtro gaussiano. Luego realizamos la detección de bordes junto con una dilatación + erosión para cerrar los espacios entre los bordes en el mapa de bordes (Líneas 28-30).
Las líneas 33-35 encuentran contornos (es decir, los contornos) que corresponden a los objetos en nuestro mapa de bordes.
Luego, estos contornos se ordenan de izquierda a derecha (lo que nos permite extraer nuestro objeto de referencia) en la Línea 39. También inicializamos nuestro valor pixelsPerMetric en la Línea 40.
En la línea 43 comenzamos a recorrer cada uno de los contornos individuales. Si el contorno no es lo suficientemente grande, descartamos la región, asumiendo que se trata de ruido proveniente del proceso de detección de bordes (Líneas 45 y 46).
Siempre que la región del contorno sea lo suficientemente grande, calculamos el cuadro delimitador girado de la imagen en las Líneas 50-52, teniendo especial cuidado en utilizar la función cv2.cv.BoxPoints para OpenCV 2.4 y el método cv2.boxPoints para OpenCV 3.
Luego, organizamos las coordenadas de nuestro cuadro delimitador girado en orden superior izquierdo, superior derecho, inferior derecho e inferior izquierdo, como se explica en la publicación del blog de la semana pasada (Línea 58).
Por último, las líneas 59-63 dibujan el contorno del objeto en verde, y luego dibujan los vértices del rectángulo delimitador en forma de pequeños círculos rojos.
Ahora que tenemos nuestro cuadro delimitador ordenado, podemos calcular una serie de puntos medios:
Las líneas 68-70 desempaquetan nuestro cuadro de límite ordenado, luego calculan el punto medio entre los puntos superior izquierda y superior derecha, seguidos por el punto medio entre los puntos inferior derecha.
También calcularemos los puntos medios entre la parte superior izquierda + parte inferior izquierda y la parte superior derecha + parte inferior derecha, respectivamente (Líneas 74 y 75).
Las líneas 78-81 dibujan los puntos medios azules en nuestra imagen, seguidos de la conexión de los puntos medios con líneas moradas.
A continuación, necesitamos inicializar nuestra variable pixelsPerMetric investigando nuestro objeto de referencia:
Primero, calculamos la distancia euclidiana entre nuestros conjuntos de puntos medios (Líneas 90 y 91). La variable dA contendrá la distancia de altura (en píxeles), mientras que dB mantendrá nuestra distancia de ancho.
Luego, verificamos en la Línea 96 para ver si nuestra variable pixelsPerMetric se ha inicializado, y si no lo ha hecho, dividimos dB por nuestro ancho de suministro, lo que nos da nuestros píxeles (aproximados) por pulgada.
Ahora que nuestra variable pixelsPerMetric ha sido definida, podemos medir el tamaño de los objetos en una imagen:
Las líneas 100 y 101 calculan las dimensiones del objeto (en pulgadas) al dividir las respectivas distancias euclidianas por el valor pixelsPerMetric (consulte la sección "Píxeles por métrica" más arriba para obtener más información sobre por qué funciona esta relación).
Las líneas 104-109 dibujan las dimensiones del objeto en nuestra imagen, mientras que las líneas 112 y 113 muestran los resultados de salida.
Resultados de medición del tamaño del objeto
Para probar nuestro script object_size.py, simplemente emita el siguiente comando:
Comentarios
Publicar un comentario