Anec-notas (V)

En estas últimas semanas he estado desarrollando una aplicación para captura de imágenes usando cámaras PointGrey. Lo primero que he de comentar es que su SDK está verdaderamente mal documentado, y salirse de los ejemplos que se instalan junto a él supone un sin fin de dolores de cabeza, así que no os extrañéis si de vez en cuando aparecen anec-notas sobre estas cámaras. En esta ocasión comentaré sólo un par.

Bayer

Para los que no sepan lo que es, os dejo la Wikipedia. Como resumen, muchas cámaras RGB no son tales, sino cámaras en escala de grises donde cada píxel captura una componente de color. Es decir, hay píxeles rojos, píxeles verdes y píxeles azules, dependiendo de la configuración del filtro. Como consecuencia, la imagen obtenida sigue siendo de un único canal, y hay que aplicarle un filtro para convertirlo a tres canales (RGB) y recuperar la información faltante (el píxel verde no captura información para el canal rojo, por ejemplo).

El SDK de las cámaras PointGrey tiene su propio conversor (obviaré los tipos de datos por simplicidad).

m_Camera->RetrieveBuffer(&m_Frame);
m_Frame.Convert(PIXEL_FORMAT_RGB8, &m_FrameAux);

Este filtro actúa usando una interpolación al más cercano, por lo que, como el lector podrá deducir, una cámara de 640×480 realmente capturaría como una cámara de 240×320, con un área de píxel (en el sensor) cuatro veces mayor. El resultado final es una imagen de muy poca calidad.

En cambio, es posible utilizar la función cvtColor de OpenCV para realizar una conversión de mejor calidad:

cv::Mat cvframe(m_Frame.GetRows(), m_Frame.GetCols(), CV_8UC1, m_Frame.GetData());
cvtColor(cvframe, cvframe, CV_BayerBG2RGB);

Además, este cambio de API conlleva una sobrecarga apenas notable tanto en consumo de memoria como en tiempo, ya que la matriz de OpenCV se crea utilizando la misma área de memoria del frame creado por el SDK de PointGrey. Obviamente si hay un overhead debido al uso de una interpolación más pesada.

Como comentario final, el tipo de conversión Bayer ha utilizar no es homogéneo entre las cámaras PointGrey, así la FireFly MV usa el indicado arriba, mientras que una BlackFly requeriría un CV_BayerBG2BGR.

Instancias

Otro detalle que  me ha dado más de un dolor de cabeza ha sido el hecho de que la aplicación que desarrollo actualmente debe mostrar en varios puntos de la ejecución la imagen en vivo de las diversas cámaras conectadas. El problema radica en que si un objeto de captura de PointGrey (la cámara) no es destruido, y luego se crea otro conectado al mismo dispositivo, errores inesperados pueden aparecer al tratar de escribir los registros, o, el que me ocurría a mí, tratar de cambiar el framerate. Ni molestarme en comentar la de tiempo que pasé buscando cualquier leak de objetos de captura por todo el código.

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.