Iluminación creativa diorama con el Arduino y el TLC5940 (5 / 11 paso)

Paso 5: Escribir el código

En primer lugar, usted necesita el TLC5940 Aduino biblioteca. Las instrucciones de instalación están fuera de fecha. La biblioteca de descargar y descomprimir en un directorio temporal. Después abra el editor de Arduino y vaya a bosquejo -> Biblioteca de importación y añadir a la biblioteca. El editor hará el resto.

Edite el archivo tlc_config.h para modificar el número de TLC5940 usas. Este proyecto ejecuta te TLCs para que la línea Lee

 #define NUM_TLCS 3 

El código es bastante sencillo desde aquí y comenta. Tengo algunos comentarios al final.

LEDController.ino

 #include "Arduino.h" #include <Tlc5940.h> #include <tlc_config.h> #include "LedController.h" // Root List for all LEDs List *lightList = NULL; // various values for iterating through the RGBs int rgbIndex = 0; int rgbLastStart = 0; boolean firstRGBIndex; int maxRGB = 252; // Handy for steping through all the LEDs // Each LED will flash, which helps find missing or incorrect connections void diag() { for(uint8_t x= 0; x < 40; x++) { if ( x > 0) { Tlc.set(x-1,0); } Tlc.set(x,1000); while(Tlc.update()); delay(500); } } /* Pause for 5 seconds so that you can pull up any diagnostic you may need. Initialize the TLC chain. Create the complete light list */ void setup() { delay(5000); Tlc.init(); Tlc.clear(); lightList = createList(); addNode(lightList, createRGBCluster1()); addNode(lightList, createLEDCluster1a()); addNode(lightList, createLEDCluster2()); } /* Increment the RGB value so it slowly moves through the list of color transitions. Keep the current time so you know when to turn on and off lights. Run through the list. */ void loop() { //diag(); rgbIndex = rgbLastStart + 1; firstRGBIndex = true; long time = millis(); iterateList(time,lightList); /* The update finishes asynchronously on the TLC's. You must wait till everything updates or your lights will display incorrect values. */ while(Tlc.update()); } /* Single link list. Most of the following functions create a node of some type and attach it to the end of a list. This system creates lists of lists for each LED array. This exposed some memory challenges as the list is using some statically allocated values and shares some of those values. Pointers would have been a wiser choice. */ List* createList(void) { List *list = (List*)malloc(sizeof(List)); list->head = NULL; list->tail = NULL; return list; } List* addNode(List* list, Node* node) { if (list != NULL && node != NULL) { if (list->head == NULL) { list->head = node; list->tail = list->head; } else { list->tail->next = node; list->tail = node; } } } Node* createNode(NodeType type, uint8_t pin) { Node *result = (Node*)malloc(sizeof(Node)); result->next = NULL; result->type = type; switch(type) { case LIST: result->value = createList(); break; case LED_RGB: result->value = createRGB(pin); break; case LED_NORMAL: result->value = createLED(pin); break; } return result; } Node* createRGBNode(List* list, uint8_t pin, Runtimes runtimes, RGB *useSettings) { Node *results = createNode(LED_RGB, pin); RGB* rgb = (RGB*)results->value; configureRGB(rgb, runtimes, useSettings); addNode(list, results); return results; } void configureRGB(RGB* rgb, Runtimes runtimes, RGB *useSettings) { if ( useSettings != NULL) { rgb->useSettings = useSettings; rgb->color = useSettings->color; rgb->runtimes = useSettings->runtimes; } else { rgb->runtimes = runtimes; } } RGB* createRGB(uint8_t pin) { RGB *result = (RGB*)malloc(sizeof(RGB)); result->pin = pin; result->color.r = 0; result->color.g = 0; result->color.b = 0; result->useSettings = NULL; return result; } Node* createLEDNode(List* list, uint8_t pin, Runtimes runtimes, uint8_t level) { Node *results = createNode(LED_NORMAL, pin); LED* led = (LED*)results->value; led->level = level; led->runtimes = runtimes; addNode(list, results); return results; } LED* createLED(uint8_t pin) { LED *result = (LED*)malloc(sizeof(LED)); result->pin = pin; result->level=0; result->runtimes.startTime=0; result->runtimes.runTime=0; result->runtimes.on=false; return result; } void setRGBLed(RGB *led) { Tlc.set(led->pin,led->color.r); Tlc.set(led->pin+1,led->color.g); Tlc.set(led->pin+2,led->color.b); } /* iterate through the list and determine the correct way to execute each node. */ void iterateList(long time, List* list) { if(list != NULL) { Node* node = list->head; while(node != NULL) { executeNode(time, node); node = node->next; } } } void executeNode(long time, Node* node) { if(node != NULL) { switch(node->type) { case LIST: iterateList(time, (List*)node->value); break; case LED_RGB: setRGB(time,(RGB*)node->value); break; case LED_NORMAL: setLED(time,(LED*)node->value); break; default: Tlc.set(1,200); Tlc.update(); break; } } else { } } /* Horrible cheating going on here. There is only one RGB list so we're going to keep some extra state and apply it to just this rgb list. blech. However, this array runs much faster by iterating through precalculated values than trying to calculate and display those values. */ void setRGB(long time, RGB* rgb) { if (rgb != NULL) { boolean cycle = time > rgb->runtimes.startTime + rgb->runtimes.wait; if ( cycle ) { if ( rgb->useSettings != NULL ) { rgb->color = rgb->useSettings->color; rgb->runtimes = rgb->useSettings->runtimes; } else { if ( firstRGBIndex ) { firstRGBIndex = false; rgbLastStart++; if ( rgbLastStart > maxRGB) { rgbLastStart = 0; } rgbIndex = rgbLastStart; } rgb->color = rgbPattern[rgbIndex++]; if ( rgbIndex > maxRGB) { rgbIndex = 0; } } rgb->runtimes.startTime = time; } setRGBLed(rgb); } } void setLED(long time, LED* led) { if (led != NULL) { long execWindow = led->runtimes.startTime + led->runtimes.runTime; if(led->runtimes.runTime == -1 || (time > led->runtimes.startTime && time < execWindow)) { led->runtimes.on = true; Tlc.set(led->pin, led->level); } else if ( time > execWindow && led->runtimes.on == true ) { led->runtimes.startTime = time + led->runtimes.wait; led->runtimes.on = false; Tlc.set(led->pin, 0); } } } /* The various LED array factory methods */ Node* createRGBCluster1(void) { int i = 0; int wait = 50; Runtimes rt = (Runtimes) { 0, 0, wait, false }; Node* rgbList = createNode(LIST, 0); List* rgbCluster1 = (List*)rgbList->value; Node* a = createRGBNode( rgbCluster1, i, rt, NULL); Node* b = createRGBNode( rgbCluster1, i+=3, rt, NULL); Node* c = createRGBNode( rgbCluster1, i+=3, rt, NULL); Node* d = createRGBNode( rgbCluster1, i+=3, rt, NULL); Node* e = createRGBNode( rgbCluster1, i+=3, rt, NULL); // Let them share values which creates a kind of cool looking // fountain effect. createRGBNode( rgbCluster1, i+=3, rt, (RGB*)e->value); createRGBNode( rgbCluster1, i+=3, rt, (RGB*)d->value); createRGBNode( rgbCluster1, i+=3, rt, (RGB*)c->value); createRGBNode( rgbCluster1, i+=3, rt, (RGB*)b->value); createRGBNode( rgbCluster1, i+=3, rt, (RGB*)a->value); return rgbList; } Node* createLEDCluster1a(void) { int i = 30; Node* ledList = createNode(LIST, 0); List* ledCluster = (List*)ledList->value; createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); createLEDNode( ledCluster, i++, (Runtimes) { -1, -1, -1, true }, 300); return ledList; } Node* createLEDCluster2(void) { int i = 36; Node* ledList = createNode(LIST, 0); List* ledCluster = (List*)ledList->value; createLEDNode( ledCluster, i++, (Runtimes) { 10000, 30000, 25000, true }, 3000); createLEDNode( ledCluster, i++, (Runtimes) { 10000, 30000, 25000, true }, 3000); createLEDNode( ledCluster, i++, (Runtimes) { 3000, 90000, 45000, true }, 3000); createLEDNode( ledCluster, i++, (Runtimes) { 3000, 90000, 45000, true }, 3000); return ledList; } /* This is some old code that did the sine wave calculation. It works but is very slow. I wrote some code to capture the values and write them out the serial console instead and then copied the values into the header void setRGBFreq(RGB *led, uint8_t i, uint8_t max) { float frequency = .3; led->r = sin(frequency*(i) + 0) * 127 + 128; led->g = sin(frequency*(i) + 2) * 127 + 128; led->b = sin(frequency*(i) + 4) * 127 + 128; uint8_t total = led->r + led->g + led->b; if ( total > max ) { led->r -= led->r/total * 100.0; led->g -= led->g/total * 100.0; led->b -= led->b/total * 100.0; } //printList(led); }*/ 

LEDController.h

 <code> #ifndef LEDController #define LEDController #define RGB_LEDS 10 typedef enum { LIST, LED_RGB, LED_NORMAL } NodeType; typedef struct { long startTime; long runTime; long wait; boolean on; } Runtimes; typedef struct { uint8_t r; uint8_t g; uint8_t b; } Colors; typedef struct rgb { Colors color; uint8_t pin; Runtimes runtimes; struct rgb *useSettings; } RGB; typedef struct { uint8_t pin; uint8_t level; Runtimes runtimes; } LED; typedef struct node { NodeType type; void* value; struct node* next; } Node; typedef struct { Node* head; Node* tail; } List; static Colors rgbPattern[] = { {128, 243, 31},{165, 222, 11},{199, 193, 1},{227, 158, 3}, {246, 120, 15},{254, 83, 38},{251, 50, 68},{237, 24, 104}, {213, 7, 142},{182, 1, 179},{145, 6, 211},{107, 22, 236}, {71, 47, 250},{40, 80, 254},{17, 117, 247},{3, 155, 229}, {1, 190, 202},{10, 220, 168},{29, 242, 131},{58, 253, 93}, {92, 253, 58},{130, 242, 30},{167, 221, 10},{201, 191, 1}, {228, 156, 3},{247, 118, 16},{254, 81, 39},{251, 48, 70}, {236, 22, 106},{212, 6, 144},{180, 1, 181},{143, 6, 213}, {105, 23, 237},{69, 49, 251},{39, 82, 254},{16, 119, 246}, {3, 157, 228},{1, 192, 200},{11, 222, 166},{31, 243, 129}, {59, 253, 91},{94, 253, 57},{132, 241, 29},{169, 219, 10}, {203, 189, 1},{230, 154, 4},{247, 116, 17},{254, 79, 41}, {250, 46, 72},{235, 21, 109},{210, 5, 147},{178, 1, 183}, {141, 7, 214},{103, 24, 238},{68, 51, 251},{37, 84, 254}, {15, 121, 245},{3, 159, 226},{1, 194, 198},{12, 223, 164}, {32, 243, 126},{61, 254, 89},{96, 252, 55},{134, 240, 27}, {171, 218, 9},{204, 187, 1},{231, 152, 4},{248, 114, 18}, {254, 77, 43},{250, 45, 74},{234, 20, 111},{208, 5, 149}, {176, 1, 185},{139, 8, 216},{101, 25, 239},{66, 52, 252}, {36, 86, 254},{14, 123, 245},{2, 161, 225},{2, 196, 196}, {12, 224, 162},{34, 244, 124},{63, 254, 87},{98, 252, 53}, {136, 239, 26},{173, 216, 8},{206, 186, 1},{232, 150, 5}, {249, 112, 20},{254, 75, 44},{249, 43, 76},{233, 19, 113}, {207, 4, 151},{174, 1, 187},{137, 8, 217},{99, 27, 240}, {64, 54, 252},{34, 88, 254},{13, 125, 244},{2, 163, 224}, {2, 198, 195},{13, 226, 160},{35, 245, 122},{65, 254, 85}, {100, 252, 51},{138, 238, 25},{175, 215, 7},{208, 184, 1}, {233, 147, 5},{249, 109, 21},{254, 73, 46},{248, 42, 78}, {231, 18, 115},{205, 4, 153},{172, 1, 188},{135, 9, 219}, {97, 28, 241},{62, 56, 253},{33, 90, 253},{12, 128, 243}, {2, 165, 222},{2, 199, 193},{14, 227, 158},{36, 246, 120}, {67, 254, 83},{102, 251, 50},{140, 237, 24},{177, 213, 7}, {128, 243, 31},{165, 222, 11},{199, 193, 1},{227, 158, 3}, {246, 120, 15},{254, 83, 38},{251, 50, 68},{237, 24, 104}, {213, 7, 142},{182, 1, 179},{145, 6, 211},{107, 22, 236}, {71, 47, 250},{40, 80, 254},{17, 117, 247},{3, 155, 229}, {1, 190, 202},{10, 220, 168},{29, 242, 131},{58, 253, 93}, {92, 253, 58},{130, 242, 30},{167, 221, 10},{201, 191, 1}, {228, 156, 3},{247, 118, 16},{254, 81, 39},{251, 48, 70}, {236, 22, 106},{212, 6, 144},{180, 1, 181},{143, 6, 213}, {105, 23, 237},{69, 49, 251},{39, 82, 254},{16, 119, 246}, {3, 157, 228},{1, 192, 200},{11, 222, 166},{31, 243, 129}, {59, 253, 91},{94, 253, 57},{132, 241, 29},{169, 219, 10}, {203, 189, 1},{230, 154, 4},{247, 116, 17},{254, 79, 41}, {250, 46, 72},{235, 21, 109},{210, 5, 147},{178, 1, 183}, {141, 7, 214},{103, 24, 238},{68, 51, 251},{37, 84, 254}, {15, 121, 245},{3, 159, 226},{1, 194, 198},{12, 223, 164}, {32, 243, 126},{61, 254, 89},{96, 252, 55},{134, 240, 27}, {171, 218, 9},{204, 187, 1},{231, 152, 4},{248, 114, 18}, {254, 77, 43},{250, 45, 74},{234, 20, 111},{208, 5, 149}, {176, 1, 185},{139, 8, 216},{101, 25, 239},{66, 52, 252}, {36, 86, 254},{14, 123, 245},{2, 161, 225},{2, 196, 196}, {12, 224, 162},{34, 244, 124},{63, 254, 87},{98, 252, 53}, {136, 239, 26},{173, 216, 8},{206, 186, 1},{232, 150, 5}, {249, 112, 20},{254, 75, 44},{249, 43, 76},{233, 19, 113}, {207, 4, 151},{174, 1, 187},{137, 8, 217},{99, 27, 240}, {64, 54, 252},{34, 88, 254},{13, 125, 244},{2, 163, 224}, {2, 198, 195},{13, 226, 160},{35, 245, 122},{65, 254, 85}, {100, 252, 51},{138, 238, 25},{175, 215, 7},{208, 184, 1}, {233, 147, 5},{249, 109, 21},{254, 73, 46},{248, 42, 78}, {231, 18, 115},{205, 4, 153},{172, 1, 188},{135, 9, 219}, {97, 28, 241},{62, 56, 253},{33, 90, 253},{12, 128, 243}, {2, 165, 222},{2, 199, 193},{14, 227, 158},{36, 246, 120}, {67, 254, 83},{102, 251, 50},{140, 237, 24},{177, 213, 7} }; // Basic Double Linked-List functions for LEDs List* createList(void); List* addNode(List* list, Node* node); Node* createNode(NodeType type, uint8_t pin); RGB* createRGB(uint8_t pin); LED* createLED(uint8_t pin); Node* createRGB(List* list, uint8_t pin, Runtimes runtimes, RGB *useSettings); Node* createLEDNode(uint8_t pin, Runtimes runTimes, uint8_t level); void iterateList(long time, List* list); void setRGBLED(long time, RGB *led); void setLED(long time, LED* led); //Cluster factories Node* createRGBCluster1(void); Node* createRGBCluster1a(void); Node* createLEDCluster2(void); void configureRGB(RGB* rgb, Runtimes runtimes, RGB *useSettings); #endif 

El código utiliza un varias listas vinculadas solo para administrar todos los LEDs, sus colores, brillo, duración y otros ajustes. Utilizando una lista enlazada fue un error y sería administrar memoria de una manera diferente. ¿Por qué? RgbPattern estáticamente asignado utiliza mucha memoria, pero la memoria es contigua. Las listas enlazadas no son contiguas por la intención, más bien por casualidad. El resultado es que puede tener pequeños bloques de memoria se asigna para cada nodo en la lista. El asignador coge el primer bloque de memoria que el nodo puede caber en. Esto resulta en el asignador dejando boquetes de la memoria pequeña entre listas y nodos. Estas brechas no son utilizables y la aplicación ya no puede asignar la cantidad máxima de memoria.

Quedarse sin memoria es un poco extraño: el Arduino se reinicia. Usted espere varios segundos y luego ver que reinicie una y otra vez, y usted consigue la idea. Escribí una función rápida, no incluida en el código, que escribiría un número de bits con un intervalo a un pin que me diera una idea de hasta qué punto tiene la aplicación. Había conectado un osciloscopio al pin y había visto los bits. Saber que estaba reiniciando, era el primer truco. El escritor pin escribió seis pedacitos dentro de la función setup() y luego escribiría cinco pedacitos en la función loop(). Los cinco bits nunca fueron exhibidos. Sólo los seis bits cada 15 o más segundos.

Entonces era sólo una cuestión de jugar un rato con algunas cosas. Encontré hacia fuera que comentando por valor de un edificio de LEDs permiten el progreso de la aplicación para el loop() y continuar corriendo. Redujo el número de colores del rgbPattern un ciclo a través y luego sin comentar el edificio. La aplicación funcionó normalmente otra vez.

Cada objeto de Color es sólo de 24 bytes, sin embargo, hay líneas de 64 con 4 objetos de Color. Un poco más de 6k pasó en la rotación de color.

Lo hubiera sido asignar un array simple para todos los nodos. Entonces habría sido un bloque de memoria llena para todos los LEDs y libera más memoria para el resto de la aplicación.

Sin embargo, la solución más probable a trabajar para una red más grande de LEDs es un tablero más grande con más memoria. Un Mega manejar fácilmente una gran cantidad de edificios.

Artículos Relacionados

Controlar múltiples LEDs con un Arduino Uno.

Controlar múltiples LEDs con un Arduino Uno.

Este instructable coversssets de instrucciones para el uso de un microcontrolador, llamado el Arduino Uno para crear diferentes secuencias de iluminación de diodos electroluminosos, más popularmente conocida como LED. Las siguientes instrucciones cub
Datalogger con un Arduino de carreras

Datalogger con un Arduino de carreras

Este es un proyecto mío que me pidió un par de veces durante un poco y pensé que sería postearlo para personas interesados. Existen algunas limitaciones actuales como la resolución de datos y sincronización de datos desde diferentes entradas, pero es
Cómo medir la temperatura con gran exactitud con un Arduino y un tablero de Sensor de temperatura de TSYS01.

Cómo medir la temperatura con gran exactitud con un Arduino y un tablero de Sensor de temperatura de TSYS01.

Mientras estudiaba en la Universidad fuimos desafiados como parte de un trabajo de curso en diseño de una caja con control de temperatura muy preciso. Si el proyecto fuera a tener éxito, múltiples cajas debían ser construido y utilizado en un proyect
Señal de tráfico / luz de freno cables con controlador Arduino

Señal de tráfico / luz de freno cables con controlador Arduino

siempre ha querido una vieja señal de tráfico y finalmente consiguió uno recientemente.  Sin embargo, fue muy simple cableado para que todas las luces estaban fijos en.  ¿Qué divertido es esto?  También quería probar un controlador Arduino y pensé qu
Controlando un Motor paso a paso con un Arduino

Controlando un Motor paso a paso con un Arduino

Este tutorial le mostrará cómo funciona un motor de paso a paso que fue rescatado de una impresora antigua con un Arduino.Paso 1: ¿Qué es un Motor paso a paso? Un motor paso a paso consta de dos partes principales: un rotor y un estator. El rotor es
ARD-e: el robot con un Arduino como un cerebro

ARD-e: el robot con un Arduino como un cerebro

cómo crear un robot de código abierto Arduino controlado por menos de $100.Esperemos que después de leer esto instructable usted será capaz de dar su primer paso en robótica. ARD-e cuesta unos $90 a $130 dependiendo de cuánto electrónica repuesto tie
Enviar datos del sensor (DHT11 & BMP180) a ThingSpeak con un Arduino, mediante cable o WiFi (ESP8266)

Enviar datos del sensor (DHT11 & BMP180) a ThingSpeak con un Arduino, mediante cable o WiFi (ESP8266)

Escribí este instructable porque Thingspeak - no importa lo fácil fijar para arriba - tiene algunos obstáculos que me topé y que, a juzgar por las reacciones, otras personas están luchando con así.Cosas que usted necesita:ArduinoEthernetShield WS5100
Etiquetas de RFID de lectura con un Arduino

Etiquetas de RFID de lectura con un Arduino

en este proyecto, aprenderás a leer una etiqueta RFID utilizando el lector de novedades ID-12 y un Arduino Duemilanove.Paso 1: Comencemos! Usaremos el ID innovaciones ID-12 para realizar la tarea de leer una etiqueta RFID. Como mínimo, requiere de +
Wii remoto IR cámara Hack con interfaz Arduino

Wii remoto IR cámara Hack con interfaz Arduino

físicamente a extraemos la cámara IR desde el control remoto Wii e interfaz con un arduino controlar un servo.La cámara de infrarrojos de Wii es una cosa maravillosa. Tiene un procesador integrado que las posiciones X e Y y el tamaño de los 4 puntos
Programación Arduino con otro Arduino

Programación Arduino con otro Arduino

Este es mi primer Instructable. En este Instructable voy a mostrarle cómo programar un Arduino con otro Arduino. No hay controladores son necesarios! Este Instructable es también útil para subir bocetos a chino ArduinoPaso 1: Cosas necesarias1. un Ar
Hyduino - automatizado hidropónicos con un Arduino

Hyduino - automatizado hidropónicos con un Arduino

Por lo tanto, usted se estará preguntando... ¿Qué es la hidroponía?Básicamente, hidroponía está creciendo plantas sin el uso de un medio tradicional de la suciedad mediante el uso de una solución de agua rica en nutrientes. Los medios utilizan para "
Tener Python hable con el Arduino Yun

Tener Python hable con el Arduino Yun

Así que quieres python 2 (corriendo al lado de tu Arduino Yun Linino ) para pernos de encendido y apagado en el lado de Arduino de la Yun. Aquí es cómo hacerlo.Paso 1:En la imagen se pueden ver dos LEDs conectados a los pines digitales 12 y 13 a trav
Controlar EL alambre con un Arduino

Controlar EL alambre con un Arduino

en este instructable le mostraré cómo controlar EL alambre con un Arduino.Lo que se necesita:EL alambre y el inversor - recomiendo http://ez-el.com/ez-el-wire/10ft-ez-el-wire-3v-inverter-kit/Arduino o cualquier microcontrolador que permite controlar
Cómo controlar un RGB LED con un Arduino

Cómo controlar un RGB LED con un Arduino

En este Instructable, yo lo se que muestra cómo controlar un LED RGB con un Arduino.Para completar este proyecto, necesitarás:1 x Arduino (estoy usando la Arduino Uno R3)1 LED x RGB3 x 150-220 ohm resistencias4 x cables de puente1 x Breadboard1 x ord