universidad nacional de san juan - unsj

11
Universidad Nacional de San Juan Facultad de Ingeniería Complemento de Informática I Temas específicos de Control I Procesamiento de órdenes de farmacia OSP Profesor: Orellana, Adrián Alumnos: Raschi, Martín Reg.: 24043 Zalazar, Lucas Reg.: 24046 2014

Upload: others

Post on 31-Oct-2021

8 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Universidad Nacional de San Juan - UNSJ

Universidad Nacional de San Juan

Facultad de Ingeniería

Complemento de Informática ITemas específicos de Control I

Procesamiento de órdenes de farmacia OSP

Profesor: Orellana, Adrián

Alumnos: Raschi, Martín Reg.: 24043Zalazar, Lucas Reg.: 24046

2014

Page 2: Universidad Nacional de San Juan - UNSJ

Introducción

El proyecto integrador final de las materias 'Complementos de Informática I' y 'Temas específicos de Control I' consistió en realizar un algoritmo en lenguaje de programación en C++ capaz de procesar las órdenes de la Obra Social Provincia tanto en el lado anverso como reverso. El procesamiento mediante el algoritmo se basó en detectar tanto la ausencia como presencia de los campos que conforman la orden, poder avisarle al usuario mediante una interfaz, en este caso la terminal del Sistema Operativo Ubuntu 12.04, cual de estos fueron los faltantes y cuales los presentes.

Para realizar el programa se utilizó la herramienta IDE Eclipse con el compilador de C++ g++, agregando las librerías de visión artificial OpenCV en su versión 2.4.8.

El proyecto tomó aproximadamente dos meses de realización, debido al tiempo que tomo familiarizarnos con algunas de las funciones de OpenCv y poder lograr que realizara lo que nosotros deseábamos.

Objetivos

1. Procesar los campos de ambos lados de las órdenes, que se encuentran en una carpeta provenientes de un escaneado previo de ellas.

2. Permitir al usuario poder recibir la información provista sobre la ausencia y/o presencia de los campos de las órdenes mediante la terminal.

3. Permitir al usuario poder ordenar la información recibida, ya sea, de mayor a menos respecto al orden de ingreso, respecto al horario de procesamiento o dejarlo en el orden por defecto en que estaban.

Page 3: Universidad Nacional de San Juan - UNSJ

Desarrollo del proyecto

El trabajo integrador fue resuelto bajo el concepto de la Programación Orientada a Objetos (POO) y se utilizo C++ como lenguaje de programación, en complemento con las librerías de visión artificial OpenCV. Se generó una clase base Orden, y se derivó de ella 2 clases: la clase Anverso y la clase Reverso. Mediante los métodos de la clase base, como así también los de las clases derivadas se realizó el procesamiento de las órdenes, el cual puede describirse en 5 pasos:

• Alineación• Chequeo y posición• Centrado• Detección de Códigos de barras• Detección de presencia o ausencia de los campos

Al tratarse de una orden donde tanto la parte del anverso como la parte del reverso, no son iguales, fue necesario tener que hacer un tratamiento particular en algunos métodos, exceptuando la alineación y la detección de códigos de barras. Ya que, independientemente de la cara de la orden, era posible realizar dichos procesamientos.

Alineación

El método de Alineación aplicado consiste en encontrar mediante la función HoughLines lineas horizontales que se encuentren dentro de la imagen, previamente habiéndola pasado a escala en grises con la función cvtColor y detectado bordes con la función Canny. La función nos entregó el corrimiento en grados de las lineas, esto nos permitió rotar la imagen con el método Rotación, tantos grados sea necesario para poder hacer uso correcto de los métodos 'Chequeo y posición' y 'Centrado' con mucha precisión.

Page 4: Universidad Nacional de San Juan - UNSJ

En la imagen anterior puede observarse, como manejando los umbrales y mediante la función puede encontrarse las lineas horizontales que nos sean útiles para poder realizar la alineación que se ve en la imagen siguiente.

Page 5: Universidad Nacional de San Juan - UNSJ

Chequeo y posición

El método Chequeo y posición es propio de cada clase derivada de la clase Orden, por lo tanto en anverso como en reverso se aplicaron métodos distintos para poder detectar la orientación.

Para el caso del anverso, se utilizó la función HoughCircles, que encuentra círculos, variando el rango de radio máximo y mínimo permitido en la búsqueda dentro de una ROI(Region of interest), en el que pueda encontrar varios círculos, extraída de la imagen original y pasado a través de un filtro Gaussiano mediante la función GaussianBlur para eliminar falsos o inexistentes círculos. De esta manera nos permitió detectar el logotipo de la Obra Social Provincia, y si no fuese posible se rota la imagen 180°, y se realiza nuevamente los pasos anteriores en el método. Con este método fue posible darle una orientación correcta, ya que la imagen podría llegar a venir dada vuelta con el logotipo hacia abajo.

Para el caso del reverso, se basó en buscar un patrón en la imagen con la función matchTemplate, que es la palabra 'ser', y que dentro de la imagen se encuentra en una cierta coordenada. Y si no es posible encontrar, se rota la imagen y se realiza de nuevo proceso de buscar el patrón.

Centrado

El método Centrado también es propio de cada clase derivada de la clase Orden, por lo tanto en anverso como en reverso se aplicaron métodos distintos para poder realizar el centrado.

Este método consiste, para el caso del anverso, en lo mismo que el método de Chequeo y posición con la diferencia que se necesitó que todas las imágenes estén ubicadas siempre en las mismas coordinas para podes realizar una correcta extracción en los campos de interés. Por lo tanto una vez encontrado el circulo, se procedió a trasladar la imagen hacia la coordenada deseada mediante las funciones getAffineTransform y warpAffine.

Para el método de Centrado propio de la clase Reverso, se utiliza el mismo procesamiento que en Chequeo y posición pero como en el caso anterior utilizando las funciones getAffineTransform y warpAffine.

Page 6: Universidad Nacional de San Juan - UNSJ

Detección Código de Barras

Básicamente el método DetectarCodigoBarra consiste, como dice su nombre, en detectar los códigos de barras presentes en el anverso, solamente habrá uno, y en el reverso, donde se encuentra los troqueles de los medicamentos.

El procedimiento se basa en la aplicación del operador de Sobel el cual es un operador diferencial discreto que calcula al gradiente en función de la intensidad de una imagen, ya sea, en forma horizontal y vertical. Seguida por una operación de diferencias entre el cálculos de gradientes, es necesario aplicar la función dilate como erode, para obtener una imagen en donde solo sea posible visualizar en forma de rectángulos los códigos de barras. Es posible que no sea 100% efectivo la detección de los códigos, debido a que en el escaneo de la imagen se nos presentó la situación en donde se pierde la mitad del código de barra. Una vez obtenidos los rectángulos se remarcaba la zona donde se encontraban y se extrajo mediante una ROI. También es posible que los troqueles vengan pegados en forma vertical, por lo cual se le realizó una rotación a 90° y se volvió a detectar los códigos, en el case que no se haya encontrado ninguno en forma horizontal.

Page 7: Universidad Nacional de San Juan - UNSJ

En las siguientes imágenes vemos como el algoritmo obtiene de la imagen el código de barra en el anverso y en el reverso.

Detección de presencia o ausencia de los campos

En el siguiente método, DetectarCampo en conjunto con el método CampoLlenoVacio, una vez que se realizó en forma correcta la alineación y el posicionamiento de la orden se procede a extraer los campos de las orden y verificar si fueron llenados correctamente o no están presente.

Para el lado reverso de la orden, los campos que nos interesan son los siguientes:

• Prescripción de Droga• RP/1• RP/2• Cantidad recetada en numero• Cantidad recetada en Letra• Fecha de prescripción• Firma del profesional• Firma de la farmacia• Troqueles

Page 8: Universidad Nacional de San Juan - UNSJ

Y para el caso del anverso de la orden:

• Nombre del paciente• Edad del paciente• DNI del paciente• Fecha de atención• Firma del paciente • Aclaración del paciente • DNI en la firma • Sello del medico • Matricula del medico • Numero de la obra social • Numero del bono • Fecha emitido • Nombre del titular

Para corroborar que el campo fue llenado, en el método CampoLlenoVacio se utilizo la función Canny, y se realiza la diferencia con una imagen del mismo tamańo que la ROI pero negro en su totalidad. Si la cantidad de pixels en blanco superan un umbral que es un porcentaje de pixels de la ROI, se considera que el campo esta completo.

El algoritmo por pantalla nos entrega la información referida a los campos, con un 1 si esta presente o un 0 si esta ausente. Además de comprobar que la cantidad de troqueles de medicamentos coincidan con la el llenado de los campos RP/1 y RP/2.

Page 9: Universidad Nacional de San Juan - UNSJ

En los pasos 'Detección de Código de Barras' y 'Detección de presencia o ausencia de los campos', se almacenó las ROI extraída de la imagen en la carpeta Campos en el directorio del proyecto que fue creado dentro del algoritmo. Estas imágenes están separadas en 2 carpetas, a lo que le corresponde si es anverso o reverso.

Page 10: Universidad Nacional de San Juan - UNSJ

El algoritmo nos permite obtener el horario en el que se realizó el procesamiento de cada una de las órdenes mediante la función de la librería time.h. Además una vez terminado de procesar, el programa nos permite realizar un ordenamiento de la información en la forma que nos parezca conveniente. Ya sea, por horario de mayor a menor, en orden de defecto, y sino poder dejarlo en el orden original.

Page 11: Universidad Nacional de San Juan - UNSJ

Conclusión

En primer instancia, el proyecto tuvo sus inconvenientes en elegir los métodos más eficientes para la realización del mismo. A medida que nos familiarizarnos con las librerías de OpenCV y con el asesoramiento del profesor a cargo de la materia, pudimos encontrar los métodos adecuados para poder resolver la problemática que se nos presentó y mediante la POO obtener tener un algoritmo más claro e interpretable.

En conclusión, se llegaron a resultados muy favorables, ya que, se alinearon y posicionaron todas las órdenes que teníamos en nuestro banco de prueba mediante funciones de OpenCV con una precisión suficiente como para alcanzar los objetivos que se plantearon. Los problemas que se nos presentaron fueron debidos al no completar de forma correcta las órdenes por los usuarios de la obra social y la mala impresión de la orden, como así también los tickets del lado reverso de la orden que cubren los campos pero en general fueron solucionadas con el criterio de verificación adoptado. El proyecto brinda una base para que pueda extenderse a interpretar los códigos de barra y detectar los caracteres ingresados en cada campo.