bclose

Usando un TFT color de 3.2”

Probando un display de tamaño medio

Objetivos

 

 
    • Presentar los gráficos color con un display TFT de 3.2”.
    • Ver los comandos básicos para dibujar puntos, líneas, textos.
    • Plotear una senoide.
    • Complicar un poco más la programación de gráficos (poco más) con las gráficas de Lissajous.

 

 

Material requerido.

Version R3  Arduino UNO o MEGA.

Display 3.2" de 320x240 color
 3.2” TFT color de Seed Studio con touch panel De 320×240 pixels.

 

Gráficos con TFT de 3.2” 320×240

 

Tenía ganas de probar un display un poco más grande de lo que habíamos usado hasta ahora, y como tenia este display rodando por la mesa., le ha tocado el turno de pasar revista.

En principio tiene unas especificaciones de los mas interesantes, pantalla de 3.2 pulgadas (O de 7.8 centímetros) lo que es un tamaño ya respetable. Resolución de 320×240 pixels, que no está mal para el tamaño y con color disponible. Además dispone de panel táctil integrado como bonus.

No es un display barato pero tenía curiosidad por ver que tal iba y como además llovía con ganas no apetecía nada salir, así que me dispuse a probarlo.

Display 3.2" de 320x240 color
Display 3.2" de 320x240 color

Lo primero que me ha gustado es que este display se comporta como un Shield que se instala directamente en un UNO o en un MEGA sin problemas. En cambio no ha querido funcionar en un DUE, porque me ha dado no sé qué problema de complicación, y e suna pena, porque me vendría de perlas la potencia del DUE para los cálculos gráficos.

Utiliza, además el bus SPI para comunicarse con nuestros Duinos sin sacrificar velocidad y me ha funcionado a la primera sin más que instalar las liberáis correspondientes, que incluyen algunos programas sencillos para mostrar las posibilidades y que ilustran magníficamente las posibilidades de este display.

¿Qué puede uno hacer con un display grafico de colores como primera prueba? Pues dibujar una senoide, por supuesto, que es un problema que ilustra perfectamente los problemas de dibujar cosas en pantalla y que además nos fuerza a hacer algunos cálculos básicos de trigonometría en tipo float (Ya os digo que llovía mucho)

Así que, como yo sé que disfrutáis mucho con las matemáticas vamos a probar con este primer programa.

 

Dibujando una senoide en el display

 

Para los que aún no hayáis salido huyendo, que sepáis que esto es tan sencillo que tendremos que buscarnos algo más difícil, porque no tiene pinta de que vaya a dejar de llevor en mucho tiempo.

Tenemos que empezar descargando la librería correspondiente Seeed_TFT_v2.0.zip e instalarla siguiendo el procedimiento habitual que describimos en la sesion correspondiente.

Instalaremos esta librería y la SPI para comunicarnos con el display, mediante las instrucciones

#include <TFTv2.h>
#include <SPI.h>

En el setup iniciaremos el display con

Tft.TFTinit();

SI colocamos el display conectado a nuestro Arduino de modo que la alimentación le quede a la izquierda, el punto (0,0) del display será la esquina superior derecha y además para despistar un poco más, usa la vertical como coordenada x y la vertical como y (A mí no me miréis mal, que yo solo soy el mensajero) iros acostumbrando.

Podemos dibujar una línea horizontal (Dejando la alimentación a la izquierda) con

Tft.drawLine(120,0,120,319,RED);             // (x0,y0) a (x1, y1)

Que dibuja una línea a la altura de x 120 a lo largo de toda la pantalla, que utilizaremos como 0 para la senoide.

El loop será muy fácil:

void loop()
  {  for ( long  i = 0 ; i<360 ; i++)
       {   float y = i * 320/360 ;
           float x = 120 + sin(  i * k ) * 110 ;
           Tft.setPixel(x,y,CYAN);
       }
     exit(0);             // Terminar el programa
  }

Para dibujar la grafica, usaremos una variable i que va tomando los valores de 0 a 360 grados, pero como el display dispone de 320 pixels de ancho tenemos que escalar el valor y por eso hacemos que y (que es la horizontal) vaya de 0 a 320 pixels cuando el Angulo varia de 0 a 360 grados, y de ahí.

float y = i * 320/360 ;

Como la función sin () en Arduino requiere que la pasemos los ángulos en radianes tenemos que convertir los grados mediante el valor en radianes para cada grado:

float k = 2 * 3.1416 /360 ;

Que calculamos una única vez para acelerar el dibujo y por eso corregimos el ángulo i en grados como i *k a radianes. Como el valor de sin() estará entre 0 y 1, no se vería mucho en pantalla si no lo multiplicamos por la mitad de la altura de la pantalla (UN poco menos en realidad para que no llegue hasta arriba del todo) y después le sumamos 120 (la mitad de la altura para que empiece centrada)

Para dibujar un pixel en la pantalla usamos

Tft.setPixel(x,y,CYAN);

Que enciende el pixel en la posición (x,y) con el color indicado

Aquí tenéis el programa completo Prog_44_1 y el resultado es más o menos así:

PLoteando la funcion sin

Como sigue lloviendo, yo tengo que hacer algo un poco más complicado y se me ha ocurrido probar a dibujar las figuras de Lissajous que seguro que os encantarán a todo aquellos que no las conozcáis.

 

Dibujando las gráficas de Lissajous

 

Según la Wikipedia las figuras de Lissajous son la superposición de dos movimientos armónicos simples en direcciones perpendiculares, y la idea es que producen unas figuras geométricas bastante sorprendentes para quien no las haya visto previamente.

Son gráficas muy sencillas de montar pero un pelín más complicadas que la simple senoide y se basan en calcular puntos en el plano cuya posición depende de un par de parámetros multiplicadores y de una diferencia de fase entre las señales.

 
  • Que no cunda el pánico. las cosas son mucho más complicadas cuando te lo explican así, pero al final es una tontería. Basta con aplicar unas formulas sencillas y listo.

 

Como en el ejemplo anterior usaremos una variable i que va barriendo de 0 a 360 grados y calcularemos la x e y de los puntos de la siguiente manera:

y = 160 + cos( p * angulo + fase) * 120 ;
x = 120 + sin( n * angulo + fase) * 110;

La grafica resultante depende de los valores enteros que hayamos dando a n y p, además del ángulo de desfase.

Vamos a empezar por lo mas sencillo, dibujando la línea media y poniendo los valores de n y p en el gráfico, mediante una función que llamaremos referencias():

void referencias()
  {  Tft.drawLine(120, 0, 120, 319, RED);      // Eje horizontal
     Tft.drawString("n = ",0,300,2,RED);       // Plot n
     Tft.drawNumber(n, 48, 300,2 , RED) ;

     Tft.drawString("p = ",150,300,2,RED);      // Plot p
     Tft.drawNumber( p, 200, 300,2 , RED) ;

     Tft.drawString("Fase = ",8,12,2,RED);     // PLot Fase
     Tft.drawNumber( fase, 84, 12,2 , RED) ;
  }

Usamos las primitivas de la librería para posicionar y Plotear en pantalla las variables de control. Ya podemos empezar con el programa principal. Primero los includes

#include <stdint.h>
#include <TFTv2.h>
#include <SPI.h>

Y algunas variables

float k = 2 * 3.1416 / 360 ;
byte n = 5 ; byte p = 3 ;
byte fase = 0 ;

float x0, y0 ;
bool inicio = true ;

Calculamos k como un factor de conversión de grados a radianes y asignamos valores iniciales a las variables de control n , p, y fase.  xo e y0 para recordar el último punto ploteado y una variable de control, de la que luego hablaremos.

void setup()
  {   //TFT_BL_ON;                // turn on the background light
      Tft.TFTinit();              //init TFT library
  }

void loop()
  {    for ( long  i = 0 ; i <= 360 ; i++)
         {  float y = 160 + cos( p * i * k + fase) * 120 ;
            float x = 120 + sin( n * i * k + fase) * 110 ;
            if (inicio)      // No dibujes la linea del primer punto
               { x0 = x ; y0 = y ;
                 inicio = false ;
               }
            //Tft.setPixel(x, y, CYAN);
            Tft.drawLine(x0,y0,x,y, CYAN);
            x0 = x ; y0 = y ;            // Guardamos x,y para luego
          }
        referencias() ;      // Plotear texto y linea media
        exit(0);             // Al finalizar, terminamos el programa

}

Calculamos x e y mediante las funciones de Lissajous, y las multiplicamos por un valor de escala de poco menos de la mitad de la altura y anchura de la pantalla para ajustar la amplitud. Y después le sumamos la mitad de la anchura y altura para centrar el gráfico.

Tengo que usar el muy poco elegante control de inicio para que no dibuje una línea inicial que desluce el gráfico (Y no os imagináis lo que me pudre el tema, pero no veo como evitarlo).

Y por último podemos dibujar un único punto con Tft.setPixel() o dibujar una línea contra el punto anterior con Tft.drawLine() que me parece más elegante.

Aquí os dejo el programa Prog_44_2  y algunos ejemplos de los gráficos que resultan:

 Lissajous 1 Lissajous 2
n = 2 / p = 1n = 2 / p = 3
 Lissajous 3 Lissajous 4
n = 4 / p = 3n = 4 / p = 5
 Lissajous 5 Lissajous 6
n = 6 / p = 5n = 7 / p = 9
 Lissajous 8 Lissajous 7
n = 8 / p = 9n = 9 / p = 11

No hemos usado la fase para distorsionar la figuras, pero seguro que los que tengáis interés podeis ir probando para ver lo que sale.

 
  • Recordad que los ángulos que pasamos a la función sin y cos, tiene que ser en radianes y no en grados. Yo he puesto fase =0 porque 0 es 0 en grados y en radianes, pero no olvidéis convertir a radianes este ángulo.
 

Y por último como seguía lloviendo he hecho un programita, Prog_44_3  que convierte el método de Lissajous en una función que acepta n, p y fase como parámetros y va lanzando en secuencia diferentes combinaciones de ambas.

Por si en vuestro barrio también sigue lloviendo, aquí os dejo un vídeo con los últimos éxitos de Lissajous en directo

En la próxima sesión probaremos el modo táctil para  ver como va. Entre tanto si queréis probar un programa con touch screen, probad a cargar el magnifico ejemplo de SeedStudio  incluido llamado paint que creo que os convencerá.

 

Resumen de la sesión

 

 
  • Hicimos nuestros primeros pinitos con un display TFT de 3.2 y color.
  • Ploteamos la senoide sin problemas.
  • Nos atrevimos con las gráficas de Lissajous para ver que tampoco era para tanto.