You are on page 1of 58

Universidad de Costa Rica

Facultad de Ingenierı́a
Escuela de Ingenierı́a Eléctrica

Desarrollo de una cámara térmica de bajo


costo implementada mediante un arduino.

Por:

Daniel Hernández Méndez

Ciudad Universitaria “Rodrigo Facio”, Costa Rica

Diciembre del 2014


Desarrollo de una cámara térmica de bajo
costo implementada mediante un arduino.

Por:
Daniel Hernández Méndez

IE-0499 Proyecto eléctrico


Aprobado por el Tribunal:

Ing. Julian Gutierrez Monge


Profesor guı́a

M.Sc. Teodoro Willink Castro Ing. Gustavo Nuñez Segura


Profesor lector Profesor lector
Dedicatoria
A mi mamá y mi papá, por su apoyo y guı́a. A mis hermanos y hermana
por competir siempre conmigo. A mis amigos y compañeros de la universi-
dad por todos los buenos momentos. Asimismo a mi amigo Carlos por sus
contribuciones académicas.

v
Reconocimiento
A mi profesor guı́a Julián Gutiérrez Monge por su ayuda y colaboración. A
mis profesores lectores por su tiempo y comentarios

vi
Resumen
En el presente documento se estudia e implementa construcción de una
cámara térmica mediante un arduino. Se hizó una investigación de los funda-
mentos teóricos que rigen el funcionamiento del sensor MLX90614. Además
se investigó el protocolo de comunicación I2C utilizado por el MLx90614 para
comunicarse con el Arduino.

En cuanto al sistema para obtener la imagen fue necesario usar el progra-


ma Processing que es el encargado de presentar una plataforma para generar
la imagen térmica y poder visualizarla en la computadora, por lo que fue
necesario implementar un protocolo de comunicación entre el Arduino y la
computadora, de modo que en todo momento uno de los dos esté hablando y
el otro escuchando, de esta forma la comunicación se da mediante el envió de
comandos.

Ademas se hizó una interfaz gráfica para poder observar fácilmente la ima-
gen térmica obtenida, y otros datos de temperatura. Finalmente, se realizaron
pruebas con la cámara térmica a diferentes resoluciones de imágenes y se ob-
servó que a mayor resolución de la imagen térmica se obtiene mayor detalle,
pero con el inconveniente de que se incrementa considerablemente el tiempo
en que se tarda en obtener la imagen.

Se concluye que es posible desarrollar una cámara térmica de bajo costo por
medio de la tecnologı́a arduino, brindando un amplio rango de funcionalidad
y ventajas que otros sistemas no ofrecen o que resultan ser muy costosos.

vii
Índice general

Índice de figuras xi

Índice de cuadros xii

Nomenclatura xiii

1 Introducción 1
1.1 Justificación . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1
1.2 Objetivos . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2
1.3 Metodologı́a . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2

2 Marco teórico 3
2.1 Plataforma Arduino . . . . . . . . . . . . . . . . . . . . . . . . 3
2.2 Processing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
2.3 Arduino y Processing . . . . . . . . . . . . . . . . . . . . . . . . 5
2.4 MLX90614 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
2.5 Servo motor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
2.6 Protocolo de comunicación del bus I2C . . . . . . . . . . . . . . 11

3 Desarrollo 15
3.1 Sensor MLX90614 . . . . . . . . . . . . . . . . . . . . . . . . . 15
3.2 Comunicación Serial Primera parte . . . . . . . . . . . . . . . . 23
3.3 Circuito Final . . . . . . . . . . . . . . . . . . . . . . . . . . . . 26
3.4 Processing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
3.5 Mapa de distribución de temperatura . . . . . . . . . . . . . . . 29
3.6 Cámara Webcam . . . . . . . . . . . . . . . . . . . . . . . . . . 31
3.7 Interfaz gráfica de usuario . . . . . . . . . . . . . . . . . . . . . 31
3.8 Creación de la aplicación . . . . . . . . . . . . . . . . . . . . . . 33
3.9 Procedimiento de uso de la cámara térmica . . . . . . . . . . . 33
3.10 Resultados de las pruebas experimentales . . . . . . . . . . . . 34
3.11 Bajo Costo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39

4 Conclusiones y recomendaciones 41
4.1 Conclusiones . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41
4.2 Recomendaciones . . . . . . . . . . . . . . . . . . . . . . . . . . 42

ix
5 Bibliografı́a 43

x
Índice de figuras

2.1 Arduino Uno (Arduino, 2014). . . . . . . . . . . . . . . . . . . . . 4


2.2 Diagrama de bloques MLX90614 (Melexis, 2013). . . . . . . . . . . 6
2.3 Campo de medición (Melexis, 2013). . . . . . . . . . . . . . . . . . 7
2.4 Fov tı́pico del MLX90614xAA (Melexis, 2013). . . . . . . . . . . . 7
2.5 Fov tı́pico del MLX90614xCI (Melexis, 2013). . . . . . . . . . . . . 8
2.6 Distribución de pines MLX90614. . . . . . . . . . . . . . . . . . . . 8
2.7 Composición interna servo motor. . . . . . . . . . . . . . . . . . . . 9
2.8 Diagrama de bloques servo motor. . . . . . . . . . . . . . . . . . . 10
2.9 Funcionamiento servo motor. . . . . . . . . . . . . . . . . . . . . . 11
2.10 Bus I2C. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11

3.1 Conexión MLX90614. . . . . . . . . . . . . . . . . . . . . . . . . . 15


3.2 Direcciones de RAM MLX90614 (Melexis, 2013). . . . . . . . . . . 17
3.3 Formato protocolo del bus MLX90614 (Melexis, 2013). . . . . . . . 18
3.4 Estructura de trama escritura (Melexis, 2013). . . . . . . . . . . . 18
3.5 Formato de lectura en el SMBus. . . . . . . . . . . . . . . . . . . . 19
3.6 Estructura de trama lectura (Melexis, 2013). . . . . . . . . . . . . 20
3.7 Conexión servos. . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
3.8 Pant/tilt bracket. (SparkFun, 2014). . . . . . . . . . . . . . . . . . 22
3.9 Limitaciones estructura. . . . . . . . . . . . . . . . . . . . . . . . . 23
3.10 Circuito final . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
3.11 Escala de colores. . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30
3.12 GUI Builer. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
3.13 GUI. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
3.14 Ajustes de esquinas. . . . . . . . . . . . . . . . . . . . . . . . . . . 34
3.15 Imagen térmica, resolución 40x40 cuadros. . . . . . . . . . . . . . . 35
3.16 Imagen térmica, resolución 50x50 cuadros. . . . . . . . . . . . . . . 35
3.17 Imagen térmica, resolución 100x100 cuadros. . . . . . . . . . . . . 36
3.18 Imagen térmica, resolución 200x200 cuadros. . . . . . . . . . . . . 36
3.19 Imagen térmica distancia 50 cm. . . . . . . . . . . . . . . . . . . . 38
3.20 Imagen térmica distancia 1 m. . . . . . . . . . . . . . . . . . . . . 38

xi
Índice de cuadros

2.1 principales caracterı́sticas Arduino Uno . . . . . . . . . . . . . . . 5

xii
Nomenclatura
ACK recibido (acknowledgement)

To Temperatura objeto.

Ta Temperatura ambiente

T SA direccion de esclavo (Slave Address)

PWM Modulación por ancho de pulso (pulse-width modulation)

GU I Interfaz gráfica de usuario (graphical user interface)

P EC chequeo de error de paquetes (Packet Error Checking)

F OV campo de visión (field of visión)

I2C Protocolo de comunicación de dos cables (Inter-Integrated


Circuit)

SCL reloj serial (serial clock)

SDA datos seriales (serial data)

xiii
1 Introducción

1.1 Justificación

Una cámara térmica es una herramienta capaz de representar la pérdida de


energı́a de un sistema, donde el método es rápido y las termografı́as que pro-
duce la cámara son un argumento preciso y convincente. El uso de una cámara
térmica, ya sea como herramienta única o combinada con otros métodos, agili-
za el trabajo de forma notable. Las termografı́as localizan con exactitud dónde
se detectan pérdidas de energı́a, sin necesidad de efectuar ninguna prueba des-
tructiva.

La idea del proyecto surge ante la necesidad de contar con una cámara
térmica desarrollada con materiales de bajo coste y fáciles de conseguir, esto
con la tarea de poder ver la temperatura de una superficie sin tener que hacer
contacto alguno con ella, motivo por el cual a este tipo de cámara térmica se
le abre un amplio campo de aplicaciones, como la inspección de instalaciones
eléctricas y poder localizar defectos en las instalaciones lograndose detectar
las perdidas energéticas.

El proyecto consiste en desarrollar una cámara térmica que a partir de


las emisiones infrarrojas del cuerpo detectado, permita medir remotamente la
temperatura de una superficie. El proyecto va a estar constituido de un sensor
infrarrojo el cual es movido por dos servo motores para escanear una área
definida de un objeto o superficie que se encuentre estática, estos conectados
a un Arduino que va a controlarlos y procesar los datos obtenidos del sensor
térmico MLX90614 por medio del uso de una librerı́a dispuesta para dicho
sensor. El sensor infrarrojo va a estar montado sobre estructura apropiada
que pueda permitir el movimiento de la misma mediante los servo motores.

El desarrollo de la cámara térmica abarca la construcción y diseño de


estructura que permita conectar y montar el sensor térmico o termómetro
infrarrojo, ası́ como el acople del circuito eléctrico al sistema microcontrolado
previamente programado, y luego crear una interfaz de software que permita
visualizar las mediciones.

1
2 1 Introducción

1.2 Objetivos
Objetivo general
Diseño y construcción de una cámara térmica de bajo costo mediante el uso
de un sensor Infrarrojo, servo motores y un arduino.

Objetivos especı́ficos
Para el desarrollo de este proyecto se establecieron los siguientes objetivos:

• Poner en funcionamiento un sistema móvil que permita el movimiento


de una estructuramediante servo motores.

• Construir el hardware basado en el sensor infrarrojo que permita ser


conectada al arduino.

• Diseñar la interfaz de software para la calibración y uso normal del


sistema.

1.3 Metodologı́a
El desarrollo del trabajo incluyó los siguientes pasos y procedimientos, listados
en secuencia:

1. Investigación bibliográfica sobre los termómetros infrarrojos, su funcio-


namiento ası́ como sus respectivas especificaciones técnicas.

2. Armar una estructura apropiada que permita montar el sistema de me-


dición.

3. Determinación de las especificaciones técnicas del arduino y los servo


motores.

4. Desarrollo de un programa para poder observar los datos provenientes


de la medición en una pantalla.

5. Verificación del programa desarrollado mediante la conexión del circuito


de prueba a la tarjeta del microcontrolador.

6. Creación de la interfaz de software de medición entre la computadora y


el microcontrolador

7. Realización de pruebas y calibración al sistema de medición ante dife-


rentes situaciones para una eficaz medición y uso normal.
2 Marco teórico

2.1 Plataforma Arduino


La placa arduino es una plataforma de computación fı́sica de código abierto,
basada en una placa con un microcontrolador y un entorno de desarrollo para
crear software para la placa. (Arduino, 2014a). El lenguaje de programación
utilizado para la programación y el control de las placas están fundamen-
tados en un lenguaje conocido como Wiring, el cual también es un entorno
de programación abierta, con aplicación directa a la creación y exploración
de prototipos electrónicos y el control de hardware en general. Propiamente,
el lenguaje mencionado para las aplicaciones Arduino se conoce simplemente
como Lenguaje de Programación Arduino, nombre asignado por sus creado-
res, Massimo Banzi, David Cuartielles, Tom Igoe, Gianluca Martino y David
Mallis.(Arduino, 2014a).
En lo que respecta al entorno para el desarrollo de los programas en este
lenguaje, este fue creado tomando como modelo al entorno de programación
Processing2, presentando este muchas similitudes al utilizado por Wiring. Es
posible comunicar a los proyectos creados bajo Arduino con distintos tipos de
software. (Arduino, 2014a).
Dentro de las principales ventajas con las que cuenta una Arduino se en-
cuentran:

• Entorno de programación simple y claro: el entorno de programación de


Arduino propone un uso fácil para principiantes y flexible para usuarios
avanzados. Esta convenientemente basado en el entorno de programación
Processing.

• Software extensible y de código abierto: el software de Arduino está


publicado bajo una licencia libre y preparado para será ampliado por
programadores experimentados. El lenguaje puede ser ampliado a través
de librerı́as de C++.

• Hardware extensible y de código abierto: Arduino esta basado en los


microcontroladores ATMEGA. Los planos de los modulos del Arduino
están publicados bajo licencia Creative Commons, por lo que los dise-
ñadores de circuitos pueden hacer su propia versión del módulo, exten-
diéndolo u optimizándolo.

3
4 2 Marco teórico

• Multi-plataforma: El software de Arduino corre en los sistemas opera-


tivos Windows, Linux y Macintosh OSX. La mayorı́a de los sistemas
microcontrolados están limitados a Windows.

• Económico: Las placas Arduino son relativamente baratas comparadas


a otras plataformas de micocontroladores.

Arduino UNO
Una de las principales caracterı́sticas que presenta la plataforma arduino es
su gran variedad de modelos, brindando la oportunidad de tener una amplia
gama para escoger el que mejor se ajuste a las necesidades que el problema a
resolver requiera.

Figura 2.1: Arduino Uno (Arduino, 2014).

El modelo a usar en este proyecto corresponde al Arduino UNO, el cual


esta basado en el microcontrolador (µC) ATmega 328. Cuenta con 14 pines de
entradas/salidas digitales de los cuales 6 se pueden usar como salidas PWM,
6 entradas analógicas, un oscilador cerámico de 16 MHz, conexión USB y un
botón reset.

Como un resumen de sus principales caracterı́sticas se tiene:

2.2 Processing
Processing es un lenguaje de programación, entorno de desarrollo y una co-
munidad online. Este lenguaje, basado en Java, fue gestado con la simplicidad
en mente, para que diseñadores, artistas, estudiantes, arquitectos, ingenieros,
matemáticos, investigadores o simplemente personas con una gran curiosidad
y motivación creativa puedan aprender a programar, sin que esto resulte un
2.3. Arduino y Processing 5

Cuadro 2.1: principales caracterı́sticas Arduino Uno

Microcontrolador ATmega328
Tensión de operación 5V
Tensión de entrada (recommendada) 7-12V
Tensión de entrada (limites) 6-20V
Pines Digitales I/O 14 (6 preveen salida PWM)
Pines analogicos de entrada 6
Corriente DC por I/O 40 mA
Corriente DC por 3.3V Pin 50 mA
Memoria Flash 32 KB (ATmega328)
SRAM 2 KB (ATmega328)
EEPROM 1 KB (ATmega328)
Velocidad del reloj 16 MHz

dolor de cabeza ni tengamos que lidiar con una alta tecnicidad computacional,
y que al mismo tiempo, disfrutemos de la flexibilidad que nos permite comu-
nicarnos con la computadora en su propia lengua, el código. (Processing, 2014)

Dentro de las ventajas con las que cuenta Processing se encuentran:

• Código abierto y de libre descarga.

• Programas interactivos con salidas 2D, 3D o PDF.

• Integración de OpenGL para aceleraciones 3D

• Multi-plataforma, corre en los sistemas operativos Wndows, Linux y


MAC OS X.

• Cuenta con más de 100 librerı́as extendiendo el núcleo del software

• Esta bien documentado, con muchos libros disponibles.

2.3 Arduino y Processing


Como se dijo, tanto Arduino como Processing son de código abierto y son
herramientas para escribir programas de manera similar ya que ambos están
basados en Wiring, lo que permite crear un ambiente familiar entre ellos, lo
cual es bastante útil a la hora de querer comunicarse el Arduino con la compu-
tadora, ya sea tanto para querer manejar el arduino o desplegar en pantalla
datos obtenidos por el Arduino. Teniendo en cuenta lo anterior se puede desa-
rrollar una interfaz gráfica con Processing capaz de manejar y manipular los
6 2 Marco teórico

datos obtenidos por Arduino, mediante la comunicación serial entre la compu-


tadora y el arduino.

2.4 MLX90614
El sensor MLX90614 desarollado por Melexis es un sensor infrarrojo para
medir temperaturas sin necesidad de contacto alguno. Tal como se ve de su
diagrama de bloques en la figura 2.2, este sensor cuenta con un amplificador de
bajo ruido, un convertidor analógico digital de alta resolución de 17 bits, una
unidad de procesamiento digital de la señal, garantizando una alta resolución y
precisión alcanzada. El sensor viene de fábrica calibrado con una salida PWM
y SMBus (System Management Bus). (Melexis, 2013).

Figura 2.2: Diagrama de bloques MLX90614 (Melexis, 2013).

Las temperaturas de ambiente (Ta) y del objeto (To) calculadas están dis-
ponibles en la RAM interna del MLX90614 con una resolución de 0, 02◦ C, y
son accesibles por las salidas tanto, con el protocolo serial de dos cables SM-
Bus (I2C o TWI) o vı́a PWM (modulación por ancho de pulso) de 10-bits. En
el caso de este proyecto se usara el protocolo I2C para comunicarse entre el
arduino y el MLX90614. (Melexis, 2013).

Este sensor además cuenta con un filtro óptico que corta el flujo radiante
visible e infrarrojo cercano, este filtro está integrado en el empaquetado para
proporcionar inmunidad al ambiente y la luz solar. (Melexis, 2013).

Campo de visión FOV


Wynne y Campbell (2011) definen el campo de visión o FOV (de sus siglas
en ingles Fiel of View) como el ángulo de incidencia al cual el sensor óptico es
2.4. MLX90614 7

sensitivo a la radiación electromagnética, que en el caso del sensor MLX90614


seria a la radiación infrarroja que emiten los cuerpos. El FOV para un sensor
MLX90614 se puede ver en la figura 2.3, que del gráfico mostrado se nota que
a menor ángulo de incidencia la sensibilidad del sensor es mayor.

Figura 2.3: Campo de medición (Melexis, 2013).

El modelo a usar en este proyecto corresponde al MLX90614ESF-DCI, ya


que este modelo cuenta con la mejor precisión y un campo de visión FOV más
estrecho de todos los modelos de la familia MLX90614. Si se observa el campo
de visión de los sensores tı́picos MLX9014xAA mostrado en la figura 2.4, se
pude notar como su FOV es muy ancho, por lo tanto con un sensibilidad menor,
pero con el modelo MLX90614DCI, donde su campo de visión se muestra en la
figura 2.5, se observa que se reduce considerablemente el FOV, traduciéndose
en una mayor sensibilidad y precisión a la hora tomar medidas de temperatura
de un punto en especifico.

Figura 2.4: Fov tı́pico del MLX90614xAA (Melexis, 2013).


8 2 Marco teórico

Figura 2.5: Fov tı́pico del MLX90614xCI (Melexis, 2013).

Distribución de pines MLX90614


En la figura 2.6 a continuación se puede la configuración de los pines del
MLX90614:

Figura 2.6: Distribución de pines MLX90614.

Que como se nota, los pines 3 y 4, corresponden a la alimentación del


sensor, en este caso se usa el modelo MLX90614ESF-DCI, que se alimenta a
3.3 V, además de los pines usados en I2C, el SCL (serial clock) la entrada
de la señal de reloj, y SDA (seria data) que es la segunda lı́nea usada para
transmitir información y corresponde a la lı́nea de datos.
2.5. Servo motor 9

2.5 Servo motor


A diferencia de los motores DC, con los servo motores es posible posicionar el
eje del motor a una especı́fica posición (ángulo) usando una señal de control, el
eje del motor se va a mantener en esta posición mientras que la señal de control
no sea cambiada, cuando la señal cambia la posicion angular del eje cambia.
Esto resulta muy útil para controlar brazos robóticos u objetos que se quieran
mover a ciertos ángulos y permanecer en esa posición. (furure electronics, s.f.)
Los servo motores pueden ser clasificados de acuerdo a su tamaño y su
torque de salida que pueden aguantar, se clasifican en servos mini, estándar y
gigantes. Usualmente los de tamaño mini y estándar pueden ser alimentados
por el Arduino directamente sin necesidad sin necesidad de fuentes externas
o controladores.
Los servo motores son pequeños, tiene una circuiterı́a de control interna y
es sumamente poderoso para su tamaño. Un servo normal o estándar tiene 42
onzas por pulgada o mejor 3kg por cm de torque, que es bastante fuerte para
su tamaño. Un servo, por consiguiente, no consume mucha energı́a.
En la figura 2.7, se muestra la composición interna de un servo motor,
se puede observar la circuiterı́a de control, el motor DC, un potenciómetro,
un juego de piñones, y la caja. También puede ver los 3 cables de conexión
externa. Uno es para alimentación Vcc (+5volts), conexión a tierra GND y el
cable blanco o amarillo es el de control.

Figura 2.7: Composición interna servo motor.

Funcionamiento
El motor del servo tiene algunos circuitos de control y un potenciómetro conec-
tado al eje central del servo motor. Este potenciómetro permite a la circuiterı́a
de control, supervisar el ángulo actual del servo motor. Si el eje está en el án-
gulo correcto, entonces el motor está apagado. Si el circuito chequea que el
10 2 Marco teórico

ángulo no es el correcto, el motor girará en la dirección adecuada hasta llegar


al ángulo correcto. El eje del servo es capaz de llegar alrededor de los 180 gra-
dos. Un servo normal se usa para controlar un movimiento angular de entre
0◦ y 180◦ .
La cantidad de voltaje aplicado al motor es proporcional a la distancia
que éste necesita viajar. Ası́, si el eje necesita regresar una distancia grande,
el motor regresará a toda velocidad. Si este necesita regresar sólo una pequeña
cantidad, el motor correrá a una velocidad más lenta. A esto se le llama control
proporcional.
En la figura 2.8 se muestra el diagrama de bloques de la composición de un
servo básico, que cuenta con una motor, seguido de un juego de engranes que
proporcionan una reducción de velocidad del motor, un sensor de posición,
que es un simple potenciómetro que está sujeto al eje, mide hacia dónde está
ubicado en todo momento, es ası́ como la tarjeta controladora sabe hacia
dónde mover al motor. Esta señal entra a un amplificador de error junto con
una señal de tensión proporcionada por el controlador PWM, y sale hasta la
entrada del motor DC indicándole cuanto debe este girar.

Figura 2.8: Diagrama de bloques servo motor.

Como se dijo anteriormente, el servo cuenta con un pin de control el cual


acepta una señal de modulación por ancho de pulso (PWM), la cual puede ser
fácilmente producida por cualquier µC como lo es la placa de Arduino. Esta
señal es la que le va a decir al servo al cual ángulo posicionarse.

La señal PWM recibida por el servo se componen únicamente de variacio-


nes en la longitud del pulso, la longitud del pulso es proporcional al ángulo al
cual el motor debe girar. El rango de la longitud del pulso corresponde a un
mı́nimo de 1 ms y un máximo de 2 ms. El pulso de 1 ms va a corresponder a
una rotación hasta un ángulo de 0◦ , y el de 2 ms a una rotación hasta 180◦ .
Cualquier pulso entre 1 ms y 2 ms va a rotar el eje del servo al correspondien-
te angulo. En la figura 2.9 se muestra la manera en lo que anterior se aplica,
donde un pulso de 1,5 ms mueve el eje a un ángulo de 90◦ .
2.6. Protocolo de comunicación del bus I2C 11

Figura 2.9: Funcionamiento servo motor.

2.6 Protocolo de comunicación del bus I2C


El bus I2C fue diseñado por Phillips a principios de los 80, para permitir una
fácil comunicación entre componentes dentro de un mismo circuito. El nombre
I2C viene de Inter-Integrated Circuit, traducido como inter circuitos integra-
dos, algunas veces es llamado IIC o I 2 C bus. El bus I2C, un protocolo que
facilita la comunicación entre microcontroladores, memorias y otros dispositi-
vos con cierto nivel de “inteligencia”, sólo requiere de dos lı́neas de señal, por
lo que es llamado TWI (Two Wire Inface) o interfaz de dos hilos. Permite el
intercambio de información entre muchos dispositivos a una velocidad acep-
table, de unos 100 Kbits por segundo. (Carletti, 2011).

La comunicación de datos del bus I2C es serial y sı́ncrona. Las dos señales
del bus son bidireccionales y de drenaje abierto, una de la señales del bus
marca el tiempo la SCL (serial clock) que es la lı́nea de los pulsos de reloj que
sincronizan el sistema y la otra que es la lı́nea usada para intercambiar datos
entro los dispositivos SDA (serial data). Ya que ambas señales son de drenaje
abierto están se deben de polarizar en estado alto por medio de resistencia de
pull-up (conectadas a la alimentación), y además todos los dispositivos conec-
tados al bus deben compartir la misma tierra. (Carletti, 2011).

Figura 2.10: Bus I2C.


12 2 Marco teórico

En la figura 2.10 se puede ver la manera en que varios dispositivos se co-


nectan al bus, y como las lı́neas están en estado alto cuando se encuentran
inactivas.

Una de los dispositivos, el cual controla todo el proceso es llamado maestro


y los dispositivos que responden al maestro son llamados esclavos.

Carletti (2011) propone una definición de los términos usados en el proto-


colo I2C, que resultan muy útiles en este proyecto:

• Maestro (Master): Dispositivo que determina los tiempos y la dirección


del tráfico en el bus. Es el único que aplica los pulsos de reloj en la lı́nea
SCL. Cuando se conectan varios dispositivos maestros a un mismo bus
la configuración obtenida se denomina ”multi-maestro”.

• Esclavo (Slave): Todo dispositivo conectado al bus que no tiene la capa-


cidad de generar pulsos de reloj. Los dispositivos esclavos reciben señales
de comando y de reloj generados desde el maestro.

• Bus libre (Bus Free): Estado en el que ambas lı́neas (SDA y SCL) están
inactivas, presentando un estado lógico alto. Es el único momento en
que un dispositivo maestro puede comenzar a hacer uso del bus.

• Comienzo (Start): Se produce cuando un dispositivo maestro ocupa el


bus, generando la condición. La lı́nea de datos (SDA) toma un estado
bajo mientras que la lı́nea de reloj (SCL) permanece alta.

• Parada (Stop): Un dispositivo maestro puede generar esta condición,


dejando libre el bus. La lı́nea de datos y la de reloj toman un estado
lógico alto.

• Dato válido (Valid Data): Situación presente cuando un dato presente


en la lı́nea SDA es estable al tiempo que la lı́nea SCL está a nivel lógico
alto.

• Formato de Datos (Data Format): La transmisión de un dato a través


de este bus consiste de 8 bits de dato (1 byte). A cada byte transmitido
al bus le sigue un noveno pulso de reloj durante el cual el dispositivo
receptor del byte debe generar un pulso de reconocimiento

• Reconocimiento (Acknowledge): El pulso de reconocimiento, conocido


como ACK (del inglés Acknowledge), se logra colocando la lı́nea de datos
a un nivel lógico bajo durante el transcurso del noveno pulso de reloj.
2.6. Protocolo de comunicación del bus I2C 13

• Dirección (Address): Todo dispositivo diseñado para funcionar en este


bus posee su propia y única dirección de acceso, preestablecida por el
fabricante. Hay dispositivos que permiten definir externamente parte
de la dirección de acceso, lo que habilita que se pueda conectar en un
mismo bus un conjunto de dispositivos del mismo tipo, sin problemas de
identificación. La dirección 00 es la denominada ”de acceso general”; a
ésta responden todos los dispositivos conectados al bus.

• Lectura/Escritura (Bit R/W): Cada dispositivo tiene una dirección de


7 bits. El octavo bit (el menos significativo) que se envı́a durante la
operación de direccionamiento, completando el byte, indica el tipo de
operación a realizar. Si este bit es alto el dispositivo maestro lee in-
formación proveniente de un dispositivo esclavo. Si este bit es bajo, el
dispositivo maestro escribe información en un dispositivo esclavo.

Además cabe mencionar que la señal de ACK (acknowledgement, confir-


mación) es enviada/recibida desde ambos lados después de cada transferencia,
haciendo que reduzcan los errores en la comunicación. (Carletti, 2001).
Las ventajas más significativas de este protocolo de comunicación son:

• Solo dos lı́neas en el bus son requeridas.

• Simple relación maestro/esclavo existente entre todos los dispositivos.

• Cada dispositivo conectado al bus es direccionado por software mediante


una única dirección.

• No hay estrictos requerimientos de tasa de baudios (baud rate), ya que


el master es el que genera la señal de reloj en el bus.
3 Desarrollo
Esta primer parte abarca desde la conexión de los dispositivos al arduino ası́
como el montaje de la estructura y la programación del arduino.

3.1 Sensor MLX90614


Lo primero en este proyecto es conectar al arduino y poner en funcionamiento
el sensor MLX90614, lo cual se va a desarrollar en los siguientes apartados.

Conexión Sensor MLX90614


Como ya se dijo anteriormente este sensor se va a conectar usando el protocolo
serial I2C al arduino, para ello el arduino va ser usado como maestro y el sensor
como esclavo. Siguiendo el diagrama de conexión de I2C de la figura 2.10, se
deben conectar las lı́neas SDA y SCL de cada dispositivo, en el caso del arduino
estas lı́neas estas situadas en los pines analógicos 4 y 5 respectivamente, en el
caso del MLX90614 serı́an los pines 2 y 1 respectivamente como se ve en la
figura 2.6. La conexión fı́sicamente se verı́a de la forma como muestra en la
figura 3.1.

Figura 3.1: Conexión MLX90614.

15
16 3 Desarrollo

Si se recuerda el diagrama de la figura 2.10, se puede notar que se conectan


unas resistencias de pull-up para mantener las lı́neas en alto mientras el bus
este libre, pero en la figura 3.1 no se observan estas resistencias, esto es debido
a que estas resistencias de pull-up se pueden implementar internamente en el
arduino por código, lo cual se explica en la siguiente sección.

Programando el protocolo I2C.


Para implementar el protocolo I2C para comunicar el arduino con el MLX90614,
se debe hacer de una forma sencilla, para ello se va a hacer uso de librerı́a ya
implementada para este propósito. Arduino proporciona una librerı́a para co-
municación I2C llamada Wire, que en realidad es muy sencilla de usar, pero
en el caso de este sensor, esta librerı́a no va a ser servir para iniciar la comuni-
cación tal como está planteada esta librerı́a, hay que realizarle unos cambios
para que funcione y agregarle funciones extra para que logre funcionar con el
MLX90614. Aparte de la librerı́a Wire de Arduino, se puede encontrar la li-
brerı́a i2cmaster desarrollada por Peter Fleury, pero igualmente a esta librerı́a
hay que realizarle algunos cambios, como renombrar y cambiar ciertos archi-
vos de la librerı́a, sin embargo, la gente de bildr.org se encargó de esta tarea y
realizo los cambios a la librerı́a para que pueda funcionar con el MLX90614,
debido a que esta librerı́a es de código abierto y ası́ la redistribuyeron en su
página de internet, por lo que solo basta con descargarla e incorporarla junto
con las demás librerı́as de arduino. (bildr, 2011)

Entonces, prosiguiendo con el protocolo I2C, lo primero es incluir la libre-


rı́a para ası́ poder hacer uso de sus funciones. Por medio de la función i2c init()
de la libreria el arduino en condición de maestro inicializa el bus I2C. Como
se mencionó anteriormente, se pueden usar las resistencias de pull-up internas
del arduino por código, para ello se va a recurrir a modificar los registros del
Arduino, especı́ficamente los registros de los puertos, investigando en la pá-
gina de Arduino, se puede encontrar que en el PORTD están mapeados los
pines digitales de 0 al 7, en el PORTB están mapeados los pines digitales de
8 al 13, y en el PORTC están mapeados los pines analógicos de 0 al 5, ası́ que
como las lı́neas SDA y SCL corresponden a los pines analógicos 4 y 5, se va
a manipular el registro PORTC para implementar las resistencias de pull-up
(Arduino, 2014c).

Entonces, lo que se hace es escribir un uno lógico en las posiciones 4 y 5 del


PORTC, de esta manera se obtiene el mismo resultado que si se conectaran
dos resistencias de pull-up en las lı́neas manteniéndolas en alto.
Ahora, para poder iniciar la comunicación con el MLX9014, se debe co-
nocer la dirección de esclavo para que el maestro (Arduino) pueda comuni-
3.1. Sensor MLX90614 17

carse directamente. Recurriendo a la hoja de datos del MLX90614 (ver en


los anexos), se encuentra que la dirección de esclavo (slave address, SA) del
MLX90614 es la 0X5A, ası́ que se va a direccionar a esa dirección para comu-
nicarse con el sensor, sin embargo, cabe mencionar que como en este caso solo
se tiene un dispositivo como esclavo conectado, se puede recurrir a la dirección
de acceso general 0x00 para acceder a él, pero esto solo en caso de no conocerse
la dirección de esclavo y que este sea el único conectado, ya que de este modo
el maestro se comunica con todos los esclavos a la vez.

De nuevo recurriendo a la hoja del fabricante, se busca las direcciones del


contenido de la RAM del MLX90614 para saber dónde se alojan la temperatura
ambiente (TA) y la de temperatura de objeto (Tobj1), ası́ que de la figura 3.2
se nota que la TA está en la dirección 0x06 y la Tobj1 en 0x07.

Figura 3.2: Direcciones de RAM MLX90614 (Melexis, 2013).

Continuando con la hoja de fabricante, se encuentra la manera de calcular


la temperatura a partir de lo obtenido en RAM, indicando que la entrega de la
temperatura se da en dos bytes, ya que el protocolo I2C limita el envió a solo
1 byte a la vez. El fabricante además proporciona una fórmula para calcular
la temperatura (válida tanto para la TA y la TO), la cual se muestra en la
ecuación 3.1 (Melexis, 2013).

T [K] = T oreg ∗ 0,02 (3.1)

Ası́ que, la temperatura disponible en RAM tienen una resolución de


0.02◦ C y está en Kelvin, el bit más significativo de los 16 bits corresponde
corresponden a una bandera (flag) que indica si hubo un error en la medición
(si vale 1 es un error). Para ejemplificar el cálculo de temperatura se considera
el número obtenido de RAM 0x3BA4, ası́ que el resultado se calcula de la
siguiente manera:

1. Se convierte a un número decimal: 0x3BA4=15268


18 3 Desarrollo

2. El numero decimal se multiplica por 0.02: 15268*0.02=305,36 K


3. Finalmente se convierte a grados Celsius: 305,36 K-273,15=32,21 ◦ C

La hoja del fabricante además dice la manera en la que debe establecer la


comunicación, y se muestra en la figura 3.3.

Figura 3.3: Formato protocolo del bus MLX90614 (Melexis, 2013).

De la figura 3.3,se observa que la secuencia para comunicarse es primero


enviar 1 bit como condición inicial, luego la dirección SA, seguido de un bit
con un valor de 1 (para un escritura Write equivale a 1), en seguida se debe
esperar por un ACK por parte del esclavo reconociendo que es la dirección co-
rrecta, si se recibe un NACK significa que el dispositivo se encuentra ocupado
y se debe esperar a que se reciba el ACK para continuar, y hasta este punto
seria lo que se necesita para iniciar la comunicación con el esclavo (el sensor
MLx90614). Justo estos son los cambios que se le deben hacer a la librerı́a
para que pueda funcionar con el MLX90614, debido a esta particular forma
de protocolo usado en el bus I2C.

Para poder hacer lo anterior mencionado se usa la función de la librerı́a


“ i2c start wait()”, que lo hace es enviar la condición de inicio, transfiere la
dirección y espera a recibir el ACK, el parámetro que recibe la función es un
byte que debe tener la estructura de trama que se muestra en la figura 3.4.

Figura 3.4: Estructura de trama escritura (Melexis, 2013).


3.1. Sensor MLX90614 19

Como la SA corresponden a 7 bits (0x5A en este caso), estos necesitan


estar en la parte alta del byte de trama, por lo que esta dirección se ingresa en
la variable dispositivo y corre a la izquierda 1 posición. Este código se veria:

int dispositivo = 0x5A<<1;


i2c_start_wait(dispositivo+I2C_WRITE);

Donde “I2C WRITE” tienen el valor de 1 lógico para indicar que se trata
de una escritura (Write) y se suma para incluirlo en el byte del parámetro que
recibe la función.

Una vez establecida la comunicación con el esclavo, lo que sigue es pregun-


tarle por el contenido de la RAM para saber las temperaturas TA y TO, para
ello debemos seguir con el protocolo de lectura mostrado en la figura 3.5.

Figura 3.5: Formato de lectura en el SMBus.

Se prosigue enviando la dirección (como comando) de donde se va leer en


RAM la temperatura, un 0x06 para TA y 0x07 para TO y esperar por un
ACK, para ello se utiliza la función i2c write(), donde el parámetro que recibe
es el byte a escribir (dirección en RAM). Seguidamente, según el protocolo
para lectura, se debe volver a enviar la condición de inicio repetida (Sr), se
usa la función i2c rep start(), con el parámetro de la dirección de esclavo SA,
pero esta vez con el formato de trama de la figura 3.6 para indicar que es
una lectura (bit menos significativo igual a 0) e inmediatamente esclavo debe
enviar un ACK. Siguiendo con la figura 3.5, el esclavo ahora envı́a los bytes
con la temperatura almacenada en RAM, comenzando el byte de la parte ba-
ja, pero antes de enviar la parte alta, el maestro le debe enviar un ACK al
esclavo para indicarle de que recibió el byte y lo mismo luego de enviar el byte
de la parte alta, para hacer esta tarea se usa la función i2c readAck(), que
lee un byte del dispositivo I2C (MLX90614) y envı́a un ACK para solicitar el
siguiente byte, y ası́ se hace para leer los bytes de la parte baja y alta, para
leer el tercer byte el PEC igual se le envı́a un ACK pero este seguido de un bit
que indique que se finalizó la lectura e informarle al esclavo de ya no envié más
bytes, se usa la función i2c readNak() para este propósito, que lee un byte del
20 3 Desarrollo

esclavo y seguidamente envı́a la condición de parada, ya con esto concluye el


ciclo de lectura. Para la escritura hay un formato parecido, pero en este caso
no interesa, ya que no se le va a modificar escribiéndole nada a los registros del
MLX. Luego de leer, el maestro debe terminar la transferencia de información
con el esclavo para dejar libre el bus I2C, para ello se usa la función i2c stop()
que cumple con esta tarea.

Figura 3.6: Estructura de trama lectura (Melexis, 2013).

Lo que sigue ahora es usar la ecuación 3.1, para calcular la temperatura


leı́da a partir de los bytes de parte alta y baja almacenados en las variables
parteAltaDatos y parteBajaDatos, estos bytes se tienen que acomodar en una
sola variable que incluya ambas partes, para ello se usa la variable datosTemp,
lo primero es aplicarle una máscara a la parte alto de los datos para hacer igual
a 0 el bit más significativo de este byte que contiene una bandera indicando si
hubo error, luego de aplicar la máscara se corre 8 posiciones hacia la izquierda
este byte para darle campo a que se situé la parte baja y formar un numero
de 2 bytes, ya con los bytes acomodados se multiplica este número por 0.02
que es el factor de temperatura de la resolución de lectura y se le resta 0.228
para hacer una corrección de temperatura, todo esto según lo indica la hoja
del fabricante para el modelo especifico de MLX90614 usado en el proyecto
(Melexis, 2013).

Y con esto finalizarı́a lo que respecta a tomar la lectura del sensor MLX,
para simplifar la hora de tomar la lectura todo esto se agrupa en la función
llamada leerSensorMLX().

Servo motores
Conexión Servo motores
Como ya se explicó los servo motores (servos, para simplificar) tienen 3 cables
a su salida que corresponden a: rojo Vcc (+5 V), negro GND (tierra) y amarillo
el de control, por lo que la conexión al arduino de los servos debe hacerse de
manera que con coincidan la alimentación y la tierra, el cable de control del
servo debe ir conectado a uno de los pines digitales del arduino, la conexión
de los servos se muestra en la figura 3.7.
3.1. Sensor MLX90614 21

Figura 3.7: Conexión servos.

Que como se nota de la figura 3.7, los servos se conectan a los pines digitales
6 y 7.

Estructura de soporte

La estructura de soporte que permita dar el movimiento a las piezas a usar en


este proyecto es la llamada “pant/tilt bracket”, mostrada en la figura 3.8.
22 3 Desarrollo

Figura 3.8: Pant/tilt bracket. (SparkFun, 2014).

Donde esta estructura consta de dos soportes y todo el hardware necesario


para poder hacer un mecanismo que pueda realizar un movimiento horizontal
/ vertical mediante dos servomotores. Encima de esta estructura es donde se
va a colocar el sensor MLX90614 permitiendo que este se pueda mover en dos
dimensiones para poder escanear un área determinada.

Programación de los servos y ajuste de la estructura

Con los servos conectados y la estructura movil armada, lo que sigue es hacer
que los servos puedan mover la estructura, para ello mediante el arduino se
procede a programar el movimiento de los mismos.

Usando la librerı́a “Servo” proporcionada por Arduino se simplifican mucho


las cosas a la hora de programar los servos, ya que, en ella se encuentran las
instrucciones para manejar mediante control PWM, y simplemente con la
librerı́a es recurrir a estas funciones para darle movimiento a ángulos que se
requiera posicionar su eje (Arduino, 2014e).
A continuación se explicaran las funciones a usar de esta librerı́a:

• Attach(): permite adjuntar el servo a un pin digital del arduino, este no


tiene que ser necesariamente un pin PWM, como parámetro esta función
recibe el pin al que se desea conectar el servo.

• Write(): Función donde el parámetro que recibe corresponde a un ángulo


entre 0 y 180 grados, controlando el eje para posicionarlo a ese ángulo
especificado.
3.2. Comunicación Serial Primera parte 23

Y con estas dos funciones de la librerı́a Servo, ya se pueden controlar a


libertad los servos.

Ahora lo que sigue es ajustar la estructura de acuerdo al movimiento de los


servos, ya que en el movimiento horizontal de la estructura no hay problema,
pero en el movimiento vertical de la estructura se deben realizar ajustes ya
que este movimiento es limitado por el tipo de montaje de la misma, ya que
como se ve en la figura 3.9, debido a que esta se sujeta con tornillos estos
impiden todo el movimiento de los 180 grados que ofrece el servo vertical.

Figura 3.9: Limitaciones estructura.

Mediante un programa de prueba, se buscó el ajuste ideal de la estructura


para que esta se puede mover en rango adecuado y que se pueda escanear todo
un área sin problemas, este rango resulto ser desde los 35◦ como lı́mite inferior
hasta los 175◦ como lı́mite superior.

3.2 Comunicación Serial Primera parte


La comunicación serial entre el arduino y processing se plantea bajo el esquema
de “Handshake” o apretón de manos, que consiste básicamente en que cuando
un dispositivo esté hablando el otro esté escuchando. Para lograr esto se debe
asegurar de que uno se encuentre enviando y el otro recibiendo comandos, para
ello el destino de la comunicación envı́a un mensaje de “ACK” al origen de esta
para confirmar la recepción del mensaje o comando. En este caso processing
es el que envı́a los comandos y el arduino se encarga de recibirlos y ejecutarlos.
24 3 Desarrollo

Los comandos que va a recibir el arduino por medio de la comunicación


del puerto serial van ser guardados en un buffer y este posteriormente va a ser
analizado para si saber es un comando valido, por medio de la función “ana-
lizarSerial()”, siempre y cuando mientras haya datos disponibles en el puerto
serial. Estos datos son en realidad los bytes de los caracteres del comando re-
cibido y estos van a ser almacenados en una variable llamada bufferSerial, que
no es más que un array de char con una longitud de 10 posiciones, el buffer
se va a terminar de llenar cuando se recibe el carácter “;” que indica el final
del comando recibido, esta función regresa un true indicando que se recibió
el comando adecuadamente, si no se recibe este carácter y se sobrepasan las
10 posiciones la función regresa un false indicando que hubo un error en la
recepción del comando serial.

Una vez con el buffer lleno, se procede a analizar el comando recibido donde
el primer carácter del comando va a corresponder a la función a ejecutar y se
lista a continuación:

• s: El comando indica cambiar el lı́mite superior del movimiento vertical


de la estructura, el comando va seguido del ángulo superior, ejemplo
“s175.00;”.

• i: El comando indica cambiar el lı́mite inferior del movimiento vertical


de la estructura, el comando va seguido del ángulo inferior, ejemplo
“i35.00;”.

• h: El comando indica modificar la posición de movimiento horizontal de


la estructura, el comando va seguido del ángulo al cual se va a mover el
servo horizontal, ejemplo “h115.34;”.

• v: El comando indica modificar la posición de movimiento vertical de la


estructura, el comando va seguido del ángulo al cual se va a mover el
servo vertical, ejemplo “v70.10;”.
t: El comando indica que se le está solicitando al arduino enviar la tem-
peratura objeto obtenida del MLX90614, ejemplo del comando “r;”.

• a: El comando indica que se le está solicitando al arduino enviar la


temperatura ambiente obtenida del MLX90614, ejemplo del comando
“a;”;

Esos serı́an los posibles comandos a enviar y recibir. Cada vez que el ar-
duino recibe un comando este debe responder con un ACK para indicar que
recibió el comando correctamente y que está listo para recibir el siguiente.
3.2. Comunicación Serial Primera parte 25

Como se vio de los ejemplos de los comandos, al recibir la posición a la que


se deben mover los servos, estos números recibidos que corresponden a los án-
gulos son números que contienen decimales y además lo que se reciben son los
bytes de los caracteres, por lo que es necesario convertir estos caracteres en un
número float. Para esta tarea se implementa la función “convertirFloat()” que
recibe como parámetros el array de char a convertir y el ı́ndice de la posición
a partir de la cual empezar a convertir, y la forma de convertir de un carácter
ASCII a un entero es simplemente restándole 48 al número hexadecimal del
byte recibido, por ejemplo si recibe el carácter 6 que recurriendo a una tabla
ASCII () corresponde a un 0x36 en decimal seria 54 y 54-48=6, por lo que de
esta manera es posible realizar la conversión de un char a un entero (ASCII,
2014). Pero ahora si se recibe el comando “v106.54;”, donde cada digito del
comando es un carácter por separado, entonces, para poder convertirlo a un
float se sigue el siguiente procedimiento empezando por el ı́ndice 1 (después
de la v):

1. Se tiene un numero v=0

2. Se revisa si el siguiente carácter es un “.” O “;”, sino es ası́, se multiplica


por 10: v=0*10=0

3. Se le resta 48 al primer carácter y se suma a v, v=(49-48)+0=1

4. Se multiplica v por 10 para dar campo al siguiente número: v=1*10=10

5. Se toma el siguiente carácter se le resta 48 y se suma a v=(48-48)+10=10

6. se vuelve a multiplicar por 10: v=10*10=100

7. De nuevo se toma el siguiente carácter y se repite el proceso anterior:


v=((54-48)+100)=106

8. Pero antes de volver a multiplicar por 10, como el siguiente carácter es


un punto, ahora no se multiplica por 10 sino que se divide por 10.

9. Se toma el carácter después del punto se le resta 48 y se divide entre 10


y se suma a v: v=106+(53-48)/10=106.5

10. Se revisa si el siguiente carácter es distinto de “;”, si no es ası́ se procede


con el siguiente carácter pero ahora se divide entre 100: v=106.5+(52-
48)/100=106.54.

11. Ahora como el siguiente carácter es un “;”, se termina la conversión.


26 3 Desarrollo

Ya con la conversión realizada se le pueden pasar a los servos los ángulos


de movimiento. La función que se encarga de interpretar el comando recibido
se llama comandoServo(), y devuelve un true si se recibió el comando correcta-
mente, en caso de haberse recibido mal devuelve un false e imprime en pantalla
el error que sucedió.

Una vez recibido el comando correctamente, este se debe remitir a los


servos para que se posicionen y seguidamente enviar a processing una confir-
mación de que se recibió el ángulo, para ello se usa el comando ACK de la
forma, siguiendo el ejemplo del comando anterior, “AV106.54;”, donde la “A”
de ACK, “V” de vertical seguido del ángulo y en conjunto significa se recibió
el ángulo de la posición vertical 106,54◦ . La función encargada de esto es la
llamada moverServos().

Lo anterior fue en caso de recibir un comando para los servos, pero si se


recibe un comando de temperatura, lo que se hace es enviar un comando de
vuelta de la forma, que contenga un ACK seguido de la temperatura solicitada.
Por ejemplo se recibe el comando “a;”, que indica que se está solicitando la
temperatura ambiente, el arduino responde con el comando “AA24.53;”, donde
la “A” es de ACK, la siguiente “A” de temperatura ambiente y seguido de la
temperatura en este caso 24.53◦ . La función encargada de los comando de
temperatura se denomina comandoTemp(), y como parámetro recibe el buffer
serial con el comando enviado por processing.

3.3 Circuito Final

Para terminar de armar el circuito se conecta un diodo laser, que va a cumplir


la función de apuntador para saber en qué punto se va a estar tomando la
temperatura objeto. El circuito final se presenta en la figura 3.10.
3.4. Processing 27

Figura 3.10: Circuito final

Para finalizar esta parte de lo que respecta al arduino, resumiendo, en el


setup se inicializa la configuración del sensor MLX90614 y los servos, como
los pines a los cuales van conectados, ası́ como la posición inicial de los ser-
vos. En el loop, que es lo que se va repetir indefinidamente, se actualiza la
temperatura en cada ciclo, y si hay datos en el puerto serial, se ejecutan las
acciones de acuerdo a los comandos recibidos como mover los servos o enviar
la temperatura.

3.4 Processing
Processing va ser usado como medio para poder generar una interfaz gráfica
mediante la cual poder controlar la cámara térmica, además de encargarse
de procesar la información obtenida del sensor de temperatura y generar el
mapa de distribución de temperatura o imagen térmica, ası́ como enviar los
comando al arduino mediante la comunicación serial.
28 3 Desarrollo

Comunicación Serial Segunda Pate

Ahora se verá la comunicación por el puerto serial pero desde la perspectiva


de processing, donde processing es el encargo de enviarle comando al Arduino
para que este los interprete y pueda ejecutar las acciones correspondientes.

Lo primero es definir la forma en que se van a enviar los comandos de


movimiento de los servos, que ya en la primera parte se definió que van a ser
los que empiezan por los caracteres “v” y “h” para las posiciones vertical y
horizontal respectivamente. Para poder escribir en el puerto serial se usa el
método de Processing llamado “write()” de la librerı́a serial, donde el paráme-
tro que recibe corresponde a la cadena de caracteres a escribir. (Processing,
2014a).

Entonces, como en el caso de los comandos de los servos se necesita una


confirmación de recibido por parte de arduino o un ACK, es necesario contar
con una forma de poder recibirlos, para ello se usa el método de processing
llamado “serialEvent()” el cual es llamado generando una interrupción al pro-
grama cada vez que hay datos en el puerto serial, estos datos son leı́dos usando
el método read() de processing. Una vez leı́dos los datos se guardan en el buffer
serial hasta que se reciba el carácter “;” indicando que es el fin del comando
recibido y dejando listo el comando para ser interpretado (Processing, 2014b).

Para enviar la posición a la cual el servo se tiene que mover, se define la fun-
ción comandoSerial(), que se encarga de enviar por el puerto serial el comando
que recibe como parámetro y además esperar el ACK del comando enviado.
El comando se envı́a como una cadena de caracteres o un string simplemente
escribiendo en el puerto serial, pero ahora se entra en un nuevo problema estos
ángulos de las posiciones a enviar corresponden a un tipo de datos float, por lo
que es necesario contar con una función que convierta de float a string para po-
der enviarlos, esta función se llama “convertFloatAString()”, que recibe como
parámetro un número float, lo redondea a dos decimales, y lo convierte a un
string. Para esperar por el ACK, se crea una función llamada esperarSerial(),
que recibe como parámetro el comando esperado, este comando esperado se
compara con lo que se encuentra en el contenido del buffer serial, si son igua-
les significa que se recibió el comando esperado, pero si son diferentes hubo
un error en la comunicación y se debe esperar un tiempo para volver a en-
viar de nuevo el comando y esperar por su respectiva confirmación de recibido.

Ahora para los comandos de temperatura, processing debe enviar el co-


mando “t” o “a” para solicitar o la temperatura objeto o la ambiente respecti-
vamente según corresponda, y luego esperar a recibir el comando que incluya
3.5. Mapa de distribución de temperatura 29

el ACK junto con la temperatura medida. Se crea la funcion tempSerial(), que


va a ser la encargada de manejar los comandos que tengan que ver con tempe-
ratura, donde esta función recibe como parámetro el modo de temperatura a
solicitar, ya sea la temperatura ambiente u objeto, luego de que recibe el modo
de temperatura se encarga de enviar el respectivo comando, e inmediatamente
después, recibir el comando enviado por arduino con la temperatura almace-
nado en el buffer serial, pero este comando recibido es un string por lo que es
necesario, primero recortarlo para eliminar las caracteres que no interesan y
segundo convertir la temperatura recibida a un float, pero en este caso no va
a ser necesario implementar nuevas funciones para cumplir esta tarea, ya que
processing cuenta con el método parseFloat() que se encarga de convertir un
string a float.

Con esto concluirı́a lo que concierne a la comunicación serial entre el ar-


duino y processing.

3.5 Mapa de distribución de temperatura


Este mapa va consistir de una representación gráfica de los datos donde los
valores individuales contenidos en una matriz son representados como colo-
res, la distribución de temperatura corresponde a como se ve gráficamente la
distribución térmica de un área determinada mediante colores, por lo que es
necesario transformar la temperatura obtenida en un color correspondiente,
pero antes de empezar con esto se explicara la forma de construir el mapa.

Cada medición de temperatura objeto recibida, va a ser almacenada en


una matriz de temperatura, que inicialmente va ser llenada con valores de -1,
con propósitos de detectar errores a la hora de analizarla, esta matriz con-
forme se vaya avanzando con el mapa de temperatura va irse llenando con
las temperaturas leı́das. De estas mediciones de temperatura se va obtener la
temperatura máxima y mı́nima escaneando toda la matriz.

A este mapa se le puede definir la cantidad de cuadros a usar y tamaño


de cada cuadro, en total el mapa debe tener un tamaño de 400x400 pixeles,
ası́ que se debe ajustar estas dos cantidades para que se obtengan los 400x400
pixeles, por ejemplo, si se usa un tamaño de cada cuadro de 10 pixeles, deben
haber 40 cuadros en las columnas y las filas, obteniéndose en total la cantidad
deseada de pixeles.

La forma de construir el mapa es ir dibujando cuadro por cuadro y a cada


cuadro se le asigna un color. Para saber qué color se le debe asignar se debe
30 3 Desarrollo

contar con una escala de colores apropiada para esta tarea, por lo que mediante
con otro programa de processing se construye una escala de colores que va estar
contenida en una imagen, donde cada pixel de la imagen va corresponder a
un color, el tamaño de la imagen debe ser de alto 1 pixel y el ancho depende
cuantos colores se usaron, un ejemplo de esta escala se muestra en la figura
3.11, donde el tamaño es 1x380 pixeles.

Figura 3.11: Escala de colores.

Teniendo una escala de colores de la forma de la figura 3.11, se puede


acceder a cada color de una forma lineal, ası́ que esta imagen construida se
importa a processing y se accede a cada pixel que representa un color como si
fuera un array por medio del uso del método de processing llamado “pixels”,
que convierte la imagen en un array y devuelve el color del pixel especificado
por un ı́ndice (Processing, 2014c).

Para definir este ı́ndice, se va a mapear el rango de temperatura desde el


mı́nimo hasta el máximo de temperatura obtenida al rango de pixeles de la
imagen, que irı́a desde cero hasta el último pixel o ultimo color. Ahora es-
te ı́ndice va a apuntar un color en especı́fico de la escala de colores, y por
medio de una variable de tipo color se extrae el color del array de la escala
de color y el cuadro del mapa de colores se pinta con este color. De la esca-
la de la figura 3.11 el rojo va a representar lo más caliente y el azul los más frio.

El procedimiento se repite sucesivamente hasta obtener el mapa de colores


completo, donde se va construir de izquierda a derecha y de arriba hacia abajo,
y cada vez que se avanza un cuadro se debe enviar el comando a los servos
para que se muevan correspondientemente a la posición del cuadro. Entonces,
para calcular la posición que se le tiene que enviar a cada servo se hace a partir
de la esquina superior izquierda y con la ayuda de unos ı́ndices sobre los ejes
X e Y del mapa, de la posición vertical se le va restando al valor máximo
vertical hasta llegar al mı́nimo y en el caso del movimiento horizontal se va
sumando al valor mı́nimo horizontal hasta llegar al valor máximo. Los valores
máximos y mı́nimos horizontal y vertical se ajustan manualmente con ayuda
de la interfaz gráfica. )
3.6. Cámara Webcam 31

3.6 Cámara Webcam

Se hace uso de una cámara webcam para tomar una foto del área a ser esca-
neada y ası́ poder hacer una comparación de la imagen térmica con una foto
tomada y poder visualizar de una mejor forma la superficie a analizar.

Para poder hacer uso de la cámara se debe importar la librerı́a “video” de


processing, y ası́ poder ajustar la resolución de la cámara ası́ como los cua-
dros por segundo con los que va a trabajar la cámara. Como lo que se quiere
es tomar una foto y no una grabación de video, se limitan los cuadros por
segundo a únicamente 5 por segundo, de esta manera con una resolución de
640x480 pixeles se puede obtener una calidad mejor de imagen y la foto se va
a ver con mayor claridad. Por esta razón la cámara se ajusta a la resolución
máxima que es de 640x480 y un framerate de 5 cuadros por segundo.

La imagen obtenida de la cámara se escala a 400x400 pixeles con motivo


de poder compararla con la imagen construida del mapa de distribución de
temperatura.

3.7 Interfaz gráfica de usuario

Lo que resta ahora es construir la interfaz gráfica de usuario o también co-


nocida como GUI, para poder manipular la cámara térmica de una mejor
manera. En processing existen muchas maneras de hacer una GUI, se puede
hacer desde cero la GUI, pero representarı́a un método complicado, ası́ que
lo más sencillo es hacer uso de las librerı́as ya existentes para crear una GUI
fácilmente.

En este proyecto se usó la librerı́a llamada “g4p controls” creada por Peter
Lager, esta librerı́a provee todo un conjunto de controles para crear un GUI
2D. Una vez importada la librerı́a se puede hacer uso del “GUI Builder” que la
librerı́a provee y se ve como se muestra en la figura 3.12. Con el GUI builder
es posible agregar botones, agregar texto, ventanas, imágenes, etc. de manera
sencilla a la hora de crear una GUI.
32 3 Desarrollo

Figura 3.12: GUI Builer.

En el caso de esta interfaz se agregaron cuatro botones:

• Inicio: inicia la secuencia de dibujo del mapa de calor.

• Pausa: permite poner pausa la secuencia de dibujo.

• Establecer esquina: este botón permite ajustar la posición de la esquina


inferior derecha del área a escanear.

• Guardar imagen: permite guardar una imagen una vez la imagen térmica
esté terminada.

Además de los botones anteriormente mencionados, se agregaron cuatro


flechas que permiten mover la estructura y que el sensor apunte a un lugar
determinado, de esta forma permitiendo ajustar el área a escanear junto con
el botón “establecer esquina”.

Se escoge un tamaño de ventana de la interfaz de 900x600 pixeles de mane-


ra que sea capaz de contener todos los elementos, ya que tiene que albergar la
imagen dibujada del mapa de calor que es de 400x400 pixeles y junto a esta la
imagen obtenida por la cámara que igualmente es de 400x400 pixeles, además
debajo de las imagen térmica, se presentan datos tales como, temperatura má-
xima, mı́nima, media, ambiente, además de la resolución de la imagen térmica
y la temperatura del cursor al situarse en un punto de la imagen térmica.
También se presenta la escala de colores para usarla como referencia a la hora
de analizar la imagen térmica. La interfaz se ve como se muestra en la figura
3.13.
3.8. Creación de la aplicación 33

Figura 3.13: GUI.

3.8 Creación de la aplicación


Una de las muchas facilidades que ofrece processing, es que proporciona la
opción de crear una aplicación para poder ejecutar el programa ya sea desde
Windows, Linux o MAC OS X, de manera muy sencilla a partir del código
fuente del programa.

Para poder ejecutar esta aplicación es necesario tener instalada la versión


7 o superior de JAVA.

3.9 Procedimiento de uso de la cámara térmica


Lo primero es abrir el archivo de la aplicación del programa o sino desde el
mismo processing, una vez mostrada la interfaz mostrada en la figura 3.14, con
ayuda de la imagen mostrada obtenida de la cámara se apunta a la superficie
de la cual se quiere obtener la imagen térmica, ya decidida la superficie se
debe por medio del apuntador laser situarse en la esquina inferior derecha de
la imagen mostrada de la cámara y presionarse el botón “establecer esquina”,
una vez hecho esto se debe ir a la esquina superior derecha y tocar el botón
iniciar para que empiece la secuencia de dibujo y se obtenga la obtenga la
imagen térmica, una vez acabada la imagen, si se desea se puede guardar esta
34 3 Desarrollo

imanen en una archivo jpg mediante el botón “guardar img”.

La razón para la cual se tiene que ir a las esquinas, es para ajustar los
lı́mites a los cuales se va a dar el movimiento de los servos, ya que estos
lı́mites cambian de acuerdo a la superficie a analizar y la distancia a la cual
se encuentra la cámara térmica de la superficie, de manera que los limites se
ajusten como se muestra en la figura 3.14.

Figura 3.14: Ajustes de esquinas.

3.10 Resultados de las pruebas experimentales

Una ves con todo el sistema de la camara termica listo se procede a realizar
pruebas, para ello se escoge una superficie que contenga un objeto caliente
y lo demás frió o a temperatura ambiente, en este caso para las pruebas se
escoge el monitor de la computadora y se realizan varias imágenes térmicas a
diferentes resoluciones tal como se muestra en las figuras 3.15, 3.16, 3.17, 3.18.
3.10. Resultados de las pruebas experimentales 35

Figura 3.15: Imagen térmica, resolución 40x40 cuadros.

Figura 3.16: Imagen térmica, resolución 50x50 cuadros.


36 3 Desarrollo

Figura 3.17: Imagen térmica, resolución 100x100 cuadros.

Figura 3.18: Imagen térmica, resolución 200x200 cuadros.

Lo primero a notar de las imágenes anteriores, es que conforme se incre-


mentan el número de cuadros se reduce el tamaño de los cuadros, provocando
3.10. Resultados de las pruebas experimentales 37

el efecto de que la imagen térmica se vea con mayor detalle la distribución


térmica, ya que de las imágenes se puede observar que el monitor tiene la
parte superior más caliente que el resto y lo demás alrededor de él esta frio en
comparación.

Un aspecto importante a mencionar es que conforme se incrementan la re-


solución de la imagen se incrementa también el tiempo que le toma en crearla,
ya que al haber mayor número de cuadros significa que el Qrduino se va tener
que mover una mayor cantidad de veces para tomar la temperatura de ese
cuadro y lo cual va a tardar más tiempo. En los casos de las imágenes anterio-
res, para la resolución de 40x40 le tomo un tiempo de 3 minutos en crearla, la
de 50x50 tomo un tiempo de 5 min, la de 100x100 23 minutos y la de 200x200
2 horas en crearla. Por lo que a mayor resolución se incrementa el tiempo que
dura en dibujar la imagen térmica. Lo cual representa un inconveniente, ya
que al tratarse de mediciones térmicas, en un tiempo grande la temperatura
puede variar totalmente provocando incongruencias en la imagen térmica ob-
tenida.

Otro aspecto importante a considerar es la distancia a la cual se va tomar


la imagen térmica de la superficie. Siguiendo con la temperatura del monitor
se realizó la imagen térmica a una distancia de unos 50 cm del monitor y se
obtuvo la imagen que se muestra en la figura 3.19, pero si ahora la distancia
se incrementa a un metro se obtiene la imagen mostrada en la figura 3.20.
38 3 Desarrollo

Figura 3.19: Imagen térmica distancia 50 cm.

Figura 3.20: Imagen térmica distancia 1 m.

Entonces de las figuras 3.19 y 3.20, se pueden notar diferencias impor-


tantes, primero la temperatura máxima disminuye, segundo la distribución
3.11. Bajo Costo 39

de temperatura no se vio muy afectada salvo que se muestra más área roja
o caliente cerca de la parte superior de la pantalla con forme se aleja y la
temperatura ambiente se incrementó.

3.11 Bajo Costo


Una parte importante del desarrollo de este proyecto es es bajo costo del
mismo, ya que si se lista a continuación los materiales usados con su respectivo
precio de compra se podrá ver el costo total:

• Arduino: $25

• Sensor MLX90614: $40

• Estructura pan/tilt bracket: $9

• Servo motores: $10

• Diodo laser: $2

• Cámara Webcam: $9

• Total: $95

Ası́ que el costo total es inferior a los $100, lo cual representa un costo
muy bajo en comparación con otras cámaras térmicas existentes en el merca-
do, donde una cámara térmica en el mercado ronda los precios desde los $1000
hasta los $8000, lo más barato encontrado es un dispositivo que se le puede
agregar a un teléfono móvil para convertirlo en una cámara térmica, pero este
cuesta más de $300. Por lo que se puede notar que este proyecto verdadera-
mente representa una opción de bajo costo y sus materiales son muy fáciles
de conseguir al estar basado este proyecto en arduino.
4 Conclusiones y recomendaciones

4.1 Conclusiones
• Se describió el proceso mediante el cual funciona el protocolo de comuni-
cación serial I2C, en el caso especı́fico del sensor termómetro infrarrojo
MLX90614.

• Se realizó una descripción general de la plataforma Arduino y Processing


y las ventajas que estos ofrecen.

• Se observó la alta compatibilidad entre Arduino y Processing a la hora


de desarrollar proyectos que ocupen comunicación entre el arduino y la
computadora.

• Se concluye que el uso de la plataforma arduino es la mejor opción para


la aplicación del proyecto debido a su bajo costo y facilidad de obtenerlo
en el mercado nacional.

• Se estudió la teorı́a básica de la comunicación serial por medio de “hands-


hake” y los elementos que la componen.

• Se logró la comunicación por el puerto serial entre el Arduino y Proces-


sing, pudiéndose transmitir los datos mediante comandos y el envió de
ACKs.

• El uso de librerı́as simplifico mucho las cosas a la hora de programar el


Arduino y Processing, ya que de esta manera no se tuvo que empezar
de cero a programar.

• Se logró exitosamente el diseño de la interfaz de software que permite


una calibración y uso normal del sistema de la cámara térmica.

• Se logró obtener la imagen térmica por medio del uso del sensor MLX90614,
servo motores y una estructura móvil que permitió escanear un área o
un objeto que se mantuviera estático.

• Se comparó diferentes imágenes térmica obtenidas a diferentes resolu-


ciones y se pudo notar como el detalle de la imagen aumenta conforme
aumentan los cuadros que compones la imanen térmica.

41
42 4 Conclusiones y recomendaciones

• El efecto de incrementar la resolución de la imagen térmica se traduce


en que se incrementa considerablemente el tiempo que toma en crearla.

• La distancia a la cual se toma la imagen térmica influye en la imagen, ya


que a mayor distancia disminuye la temperatura medida por el sensor.

• Se recomienda no usar grandes resoluciones de la imagen termica en


procesos en los que varı́a rápidamente la temperatura, ya que la imagen
va a tomar mucho tiempo en crearse y se van a presentar incongruencias
de temperatura en la imagen.

4.2 Recomendaciones
• Se recomiendo el uso modelo del sensor MLX90614 utilizado en este
proyecto, ya que ofrece una mayor precisión y un menor campo de visión,
que se traduce en mejores medición a mayores distancias.

• Se recomienda el uso de librerı́as ya que simplifican mucho el trabajo a


la hora de programar.

• Se recomienda estudiar la posibilidad del uso de un sensor ultrasónico


para además de obtener una imagen térmica se obtenga una imagen
acústica en conjunto y que se pueda mapear el área con las distancias
de la temperatura tomada.

• Se recomienda mejorar la interfaz gráfica de usuario añadiendo más fun-


ciones y mejorar la calidad de la imagen obtenida.

• Se recomienda el uso de otra plataforma con mejores caracterı́sticas que


el arduino para ası́ poder obtener en menor tiempo la imagen termica.

• Se deja como ampliación del sistema añadir un display LCD para no


tener que hacer uso de la computadora para poder visualizar la imagen
y ası́ directamente poder ver imagen térmica obtenida en menor tiempo.
5 Bibliografı́a
Arduino (2014a). Arduino. Recuperado de http://arduino.cc/es/Guide/Introduction.

Arduino (2014b). Arduino board uno. Recuperado de http://arduino.


cc/en/Main/ArduinoBoardUno.

Arduino (2014c). Port registers. Recuperado de http://www.arduino.


cc/en/pmwiki.php?n=Reference/PortManipulation

Arduino (2014d). Wire Library. Recuperado de http://arduino.cc/


en/pmwiki.php?n=Reference/Wire

Arduino (2014e). Servo Library. Recuperado de http://arduino.cc/


en/pmwiki.php?n=Reference/Servo

ASCII (2014). Tabla de códigos ASCII. Recuperado de http://ascii.


cl/es/

Bildr (2011). Is it hot? Arduino + MLX90614 IR Thermometer. Recu-


perado de http://bildr.org/2011/02/mlx90614-arduino/

Carletti, E. (2007). Comunicación - Bus I2C. Recuperado de http://


robots-argentina.com.ar/Comunicacion_busI2C.htm

Campbell, J & Wynne, R. (2011). Introduction to remote sensing (5ta


ed.). New York: Guilford Press.

Future Electronics (2011). Servo motors control and Arduino. Recu-


perado de http://www.fut-electronics.com/wp-content/plugins/
fe_downloads/Uploads/Introduction\%20to\%20Servo\%20Motors\%20&\
%20Arduino.pdf

Melexis (2013). MLX90614 Familyl, Single and Dual Zone Infra Red
Thermometer in TO-39. Recuperado de http://www.adafruit.com/
datasheets/MLX90614.pdf

Processing (2014a). Serial. Recuperado de https://processing.org/


reference/libraries/serial/

Processing (2014b). Serial event. Recuperado dehttps://processing.


org/reference/libraries/serial/serialEvent_.html

43
44 5 Bibliografı́a

Processing (2014c). Pixels. Recuperado de https://www.processing.


org/reference/pixels.html

Sparkfun (2014a). Connecting Arduino to Processing. Recuperado de


https://learn.sparkfun.com/tutorials/connecting-arduino-to-processing

Sparkfun (2014b). Pan/Tilt Bracket. Recuperado de https://www.sparkfun.


com/products/10335

You might also like