TALLER DE DISEÑO DE ENTORNOS DIGITALES 06. Las formas del tiempo ClockoBlock: Yugo Nakamura 2001, http://surface.yugop.com/ Objetivo La manera de representar el transcurrir del tiempo ha estado tradicionalmente ligada a las tecnologías utilizadas en la producción de relojes y dispositivos análogos. Relojes de arena, de sol, péndulos, relojes de agujas, de cuarzo, digitales … la manera con la que estos objetos contestan a nuestra pregunta: “¿ Que hora es ?” esta condicionada por las características y las limitaciones de la tecnología utilizada. Este hecho ha comportado un amplio abanico de soluciones, a menudo originales e ingeniosas; a algunas de ellas se le podría denominar hoy “multimedia”. En un contexto digital podemos afrontar la creación de un “reloj” con mayor libertad expresiva que nunca. La hora en formato digital, aplicación mínima: Usa el siguiente código para acceder desde Processing a la hora marcada por tu ordenador: PFont font; int h,m,s; void setup(){ size(400,400); smooth(); font = loadFont("HelveticaNeue-Bold-48.vlw"); } void draw() { background(255); // accede a hora, minutos, segundos s = second(); // valores entre 0 - 59 CC – some rights reserved - Alfredo Calosci 2009. 1 TALLER DE DISEÑO DE ENTORNOS DIGITALES m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // escribe la Hora fill(0); textAlign(CENTER,CENTER); textFont(font, 48); String hora = h + ":" + m + ":" + s; text(hora, width/2, height/2); } Las funciones: hour(), minute() y second() “leen” la hora marcada por el ordenador. La variable de texto – String – “hora” junta estos valores en un único texto separado por “:”. Para “formatear” el texto y “forzar” los dos dígitos ( 01, 02, 03 …) modifica draw() como sigue: void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // escribe la Hora fill(0); textAlign(CENTER,CENTER); textFont(font, 48); String hora = nf(h,2) + ":" + nf(m,2) + ":" + nf(s,2); text(hora, width/2, height/2); } La función nf() nos permite definir cuantos digitos queremos utilizar cuando convertimos un numero, entero o decimal, a texto ( String ). Añadimos la fecha PFont font; int h,m,s; int dia, mes, anno; void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // la fecha dia = day(); // 1 > 31 mes = month(); // 1 > 12 anno = year(); // escribe la Hora fill(0); textAlign(CENTER,CENTER); textFont(font, 48); String hora = nf(h,2) + ":" + nf(m,2) + ":" + nf(s,2); text(hora, width/2, height/2); // escribe la Fecha fill(128); textFont(font, 24); text(dia + "/" + mes + "/" + anno, width/2, height*3/4); } Accedemos a la fecha que nos proporciona el ordenador por medio de las funciones: day(), month() y year(). Escribir el mes en forma de texto: Arrays Processing “no conoce” el nombre de los meses en los diferentes idiomas (en el calendario gregoriano, implantado en 1582 y actualmente adoptado por un gran numero de países). Para utilizar los nombres de los meses en castellano tendremos que crear un “Array” de textos (String). CC – some rights reserved - Alfredo Calosci 2009. 2 TALLER DE DISEÑO DE ENTORNOS DIGITALES Un “Array” es un contenedor “genérico” de “objetos”, textos en nuestro caso, a los que podremos acceder desde la aplicación. PFont font; int h,m,s; int dia, mes, anno; String[] meses = new String[12]; La sintaxis de la nueva línea de código podría leerse así: Crea una variable de nombre “mese” que será un “contenedor” de 12 textos. En setup() “llenaremos” nuestro contenedor con los 12 nombres de los meses. void setup(){ size(400,400); smooth(); font = loadFont("HelveticaNeue-Bold-48.vlw"); // asigna el texto correspondiente a cada mes meses[0] = "enero"; meses[1] = "febrero"; meses[2] = "marzo"; meses[3] = "abril"; meses[4] = "mayo"; meses[5] = "junio"; meses[6] = "julio"; meses[7] = "agosto"; meses[8] = "septiembre"; meses[9] = "octubre"; meses[10] = "noviembre"; meses[11] = "diciembre"; } Observa que el primer elemento de un array, contrariamente a lo que podríamos esperar, no es el elemento numero “1” sino el numero “0”; por eso para asignar el texto “enero” al primer elemento del Array usamos la instrucción: meses[0] = "enero"; Modifica Draw() y crea una función específica: “textos()” para escribir los textos relativos a hora y fecha. Será suficiente cortar las instrucciones que ahora están en draw() y pegarlas entre las llaves de la nueva función textos(). void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // la fecha dia = day(); // 1 > 31 mes = month(); // 1 > 12 anno = year(); // escribe los textos textos(); } void textos(){ // escribe la Hora fill(0); textAlign(CENTER,CENTER); textFont(font, 48); String hora = nf(h,2) + ":" + nf(m,2) + ":" + nf(s,2); text(hora, width/2, height/2); // escribe la Fecha fill(128); textFont(font, 24); text(dia + "/" + meses[mes-1] + "/" + anno, width/2, height*3/4); } CC – some rights reserved - Alfredo Calosci 2009. 3 TALLER DE DISEÑO DE ENTORNOS DIGITALES Para escribir el mes en forma de texto, en lugar del numero progresivo entre 1 y 12, utiliza la expresión: meses[mes-1]; Trabajar con “unidades de segundos”: Para “animar” la visualización de la hora podemos introducir elementos cíclicos. Un ejemplo sencillo podría ser introducir un “punto rojo” que cruza la pantalla en 10 segundos. Añade en draw() el siguiente código: void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // la fecha dia = day(); // 1 > 31 mes = month(); // 1 > 12 anno = year(); // escribe los textos textos(); // un punto rojo cruza la pantalla cada 10 segundos int us = second() % 10; fill(#CC0000); noStroke(); ellipse((width/9)*us, height/4, 24,24); } En el creamos una nueva variable “unidades de segundos” que será igual al “modulo” de los segundos divididos por 10. El modulo es el resto de la división y su símbolo en Processing es “%” (valor porcentual). Interpolando el movimiento Utilizando el método que ya conocerás, arrastra a la ventana de código una copia del fichero – “integrator.pde” – que utilizaremos para interpolar el movimiento del punto rojo. En las primeras líneas de código, crea una nueva variable del tipo “integrator” para interpolar el movimiento del punto rojo. PFont font; int h,m,s; int dia, mes, anno; String[] meses = new String[12]; // animación Integrator xPunto = new Integrator(0); Y actualiza su valor en draw() modificando el código como sigue: void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // la fecha dia = day(); // 1 > 31 mes = month(); // 1 > 12 anno = year(); // escribe los textos textos(); // un punto rojo cruza la pantalla cada 10 segundos int us = second() % 10; xPunto.target(us); xPunto.update(); fill(#CC0000); CC – some rights reserved - Alfredo Calosci 2009. 4 TALLER DE DISEÑO DE ENTORNOS DIGITALES noStroke(); ellipse((width/9)*xPunto.value, height/4, 24,24); } El punto rojo deja un rastro Una manera para aprovechar los “Arrays” podría ser utilizarlo para registrar los valores anteriores de la coordenada x de nuestro “Punto Rojo” y crear así la ilusión de que el punto vaya dejando un rastro por la pantalla. En primer lugar crea un “Array” de numeros decimales (float) donde guardaremos las anteriores coordenada del punto rojo. PFont font; int h,m,s; int dia, mes, anno; String[] meses = new String[12]; // animación Integrator xPunto = new Integrator(0); // rastro int num = 48; float mx[] = new float[num]; A continuación añade el siguiente código en draw(): void draw() { background(255); // accede a Hora, Minutos, Segundos s = second(); // valores entre 0 - 59 m = minute(); // valores entre 0 - 59 h = hour(); // valores entre 0 – 23 // la fecha dia = day(); // 1 > 31 mes = month(); // 1 > 12 anno = year(); // escribe los textos textos(); // un punto rojo cruza la pantalla cada 10 segundos int us = second() % 10; xPunto.target(us); xPunto.update(); fill(#CC0000); noStroke(); ellipse((width/9)*xPunto.value, height/4, 24,24); // Rastro // Lee los valores y los "mueve" a la "izquierda" en el array: // 1>0, 2>1, 3 >2 ... for(int i=1; i<num; i++) { mx[i-1] = mx[i]; } // Añade el último valor (en el último lugar) mx[num-1] = (width/9)*xPunto.value; // bucle entre los valores registrados // el tamaño de la ellipse es cada vez mayor: i/2 // ½, 2/2, 3/2, 4/2 … 48/2 fill(#CC0000,128); for(int i=0; i<num; i++) { ellipse(mx[i], height/8, i/2, i/2); } } CC – some rights reserved - Alfredo Calosci 2009. 5 TALLER DE DISEÑO DE ENTORNOS DIGITALES Bibliografía: Ben Fry, “Visualizing Data” O’ Reilly, Cambridge 2007 Referencias: (ClockBlock 1.0) http://www.yugop.com/ http://yugop.com/ver3/index.asp?id=29 http://www.processing.org http://www.arquimatica.com/UEM CC – some rights reserved - Alfredo Calosci 2009. 6