#include "Adafruit_NeoPixel.h" const uint32_t light_line[16][6] = { { 0, 0, 4095, 4095, 0, 0}, { 0, 0, 4095, 4095, 0, 0}, { 0, 0, 4095, 4095, 0, 0}, {4095, 4095, 0, 0, 4095, 4095}, {4095, 4095, 0, 0, 4095, 4095}, { 0, 0, 4095, 4095, 0, 0}, { 0, 0, 4095, 4095, 0, 0}, { 0, 0, 4095, 4095, 0, 0}, {4095, 4095, 0, 0, 4095, 4095}, {4095, 4095, 0, 0, 4095, 4095}, { 0, 0, 0x00FF00FF, 0, 0, 0}, { 0, 0, 0, 0, 0, 0}, { 0, 0, 0x00FFFF00, 0x00FFFF00, 0, 0}, { 0, 0, 0x00FF00FF, 0, 0, 0},//0x00FF0030, { 0, 0, 0, 0, 0, 0}, { 0, 0, 0x00FFFF00, 0, 0, 0}};//0x00FF5F00 const uint32_t time_line[16][6] = { { 0, 8300, 10000, 12000, 14000, 24000}, { 0, 10000, 11300, 13800, 15000, 24000}, { 0, 13200, 15000, 16000, 17500, 24000}, { 0, 6500, 8500, 16000, 17300, 24000}, { 0, 2000, 3000, 18000, 18600, 24000}, { 0, 6000, 7800, 11200, 13000, 24000}, { 0, 10000, 11800, 15000, 17000, 24000}, { 0, 14200, 17200, 19000, 20600, 24000}, { 0, 5200, 7000, 21000, 23000, 24000}, { 0, 3000, 4200, 22800, 24000, 24000}, { 0, 6200, 7900, 9100, 13000, 24000}, { 0, 0, 0, 0, 0, 0}, { 0, 15000, 16700, 17500, 18900, 24000}, { 0, 3800, 6000, 7300, 16500, 24000}, { 0, 0, 0, 0, 0, 0}, { 0, 19500, 21500, 23500, 24000, 24000}}; static uint32_t time_canal[16] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}; //TLC5940NT pin definitions #define SIN MOSI // MOSI - Hardware SPI, can't be changed #define SCLK SCK // SCK - Hardware SPI, can't be changed #define VPRG 2 #define XLAT 4 #define BLANK 5 #define DCPRG 6 #define GSCLK 7 #define CTS 3 #define PIN 8 #define NUM_LEDS 36 Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LEDS, PIN, NEO_GRB + NEO_KHZ800); int level[16] = { 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095 }; const int remap[10] = { 1,2,3,4,5,6,7,8,9,10}; char spi_transfer(volatile byte data) { SPDR = data; // Start the transmission while (!(SPSR & (1<=0; i--){ spi_transfer( ((long)level[2*i+1] & 0x0FF0) >> 4 ); spi_transfer( (((long)level[2*i+1] & 0xF) << 4) | (((long)level[2*i] & 0x0F00) >> 8) ); spi_transfer( (long)level[2*i] & 0xFF); } PORTD |= B00010000; //digitalWrite(XLAT,HIGH); PORTD &= B11101111; //digitalWrite(XLAT,LOW); PORTC &= B10111111; // digitalWrite(BLANK, LOW); } void startup(){ //Setup the Hardware SPI registers // SPCR = 01010000 //interrupt disabled,spi enabled,msb 1st,master,clk low when idle, //sample on leading edge of clk,system clock/4 (fastest) byte clr; SPCR = (1<= tiempo_ciclo) { Serial.println("Vuelta"); for (int canal=0; canal<10;canal++) { level[remap[canal]] = light_line[canal][0]; time_canal[canal] = 0; } for (int canal=10; canal<16; canal++) { time_canal[canal] = 0; levelRGB = light_line[canal][0]; int red = (0x000000FF&(levelRGB>>16)); int green = (0x000000FF&(levelRGB>>8)); int blue = (0x000000FF&(levelRGB)); for (int num=0; num10) temp_time_resolution = time_resolution; else temp_time_resolution = time_resolution; if ((time_millis - time_canal[i])>=temp_time_resolution) { correc = (time_millis - time_canal[i])/temp_time_resolution; time_canal[i] = time_millis; if (i<10) { if (j>0) paso[i] = (((float)((int)light_line[i][j] - (int)light_line[i][j - 1]))/((time_line[i][j] - time_line[i][j - 1])*factor)*temp_time_resolution*correc) + paso[i]; else paso[i] = 0; if ((paso[i]>=1)||(paso[i]<=-1)) { temp_levelref = level[remap[i]] + paso[i]; if (temp_levelref<0) level[remap[i]] = 0; else if (temp_levelref>4095) level[remap[i]] = 4095; else level[remap[i]] = temp_levelref; setGreys(); paso[i]=0; } } else { if ((light_line[i][j]!=light_line[i][j - 1])&&(j>0)) { byte temp_i = i-10; if (j>0) { byte temp_red = (0x000000FF&(light_line[i][j]>>16)); byte temp_green = (0x000000FF&(light_line[i][j]>>8)); byte temp_blue = 0x000000FF&(light_line[i][j]); byte temp_red_ant = (0x000000FF&(light_line[i][j-1]>>16)); byte temp_green_ant = (0x000000FF&(light_line[i][j-1]>>8)); byte temp_blue_ant = 0x000000FF&(light_line[i][j-1]); // if ((time_millis>=(time_line[i][j]*factor - temp_time_resolution))&&(light_line[i][j-1]>light_line[i][j])) // { // pasoR[temp_i] = -100; pasoG[temp_i] = -100; pasoB[temp_i] = -100; //// else { pasoR[temp_i] = -10; pasoG[temp_i] = -10; pasoB[temp_i] = -10;} // } // else { pasoR[temp_i] = (((float)((int)temp_red - (int)temp_red_ant))/((time_line[i][j]- time_line[i][j - 1])*factor))*temp_time_resolution*correc + pasoR[temp_i]; pasoG[temp_i] = (((float)((int)temp_green - (int)temp_green_ant))/((time_line[i][j] - time_line[i][j - 1])*factor))*temp_time_resolution*correc + pasoG[temp_i]; pasoB[temp_i] = (((float)((int)temp_blue - (int)temp_blue_ant))/((time_line[i][j] - time_line[i][j - 1])*factor))*temp_time_resolution*correc + pasoB[temp_i]; } // if ((i==12)||(i==14)) // { // Serial.print(temp_red); // Serial.print(' '); // Serial.print(temp_green); // Serial.print(' '); // Serial.println(temp_blue); // } } else { pasoR[temp_i] = 0; pasoG[temp_i] = 0; pasoB[temp_i] = 0; } if ((pasoR[temp_i]>=1)||(pasoG[temp_i]>=1)||(pasoB[temp_i]>=1)||((pasoR[temp_i]<=-1)||(pasoG[temp_i]<=-1)||(pasoB[temp_i]<=-1))) { // if ((i==12)||(i==14)) // { // Serial.print(pasoR[temp_i]); // Serial.print(' '); // Serial.print(pasoG[temp_i]); // Serial.print(' '); // Serial.println(pasoB[temp_i]); // } // levelRGB = strip.getPixelColor((temp_i)*quantity); // if ((i==12)||(i==14)) // { // Serial.println(levelRGB, HEX); // } // float red = (int)(0x000000FF&(levelRGB>>16)) + pasoR[temp_i]; // float green = (int)(0x000000FF&(levelRGB>>8)) + pasoG[temp_i]; // float blue = (int)(0x000000FF&(levelRGB)) + pasoB[temp_i]; red[temp_i]= red[temp_i] + pasoR[temp_i]; green[temp_i] = green[temp_i] + pasoG[temp_i]; blue[temp_i] = blue[temp_i] + pasoB[temp_i]; if (red[temp_i] < 0) red[temp_i] = 0; else if (red[temp_i] > 255) red[temp_i] = 255; if (green[temp_i] < 0) green[temp_i] = 0; else if (green[temp_i] > 255) green[temp_i] = 255; if (blue[temp_i] < 0) blue[temp_i] = 0; else if (blue[temp_i] > 255) blue[temp_i] = 255; for (int num=0; num=1)||(pasoR[temp_i]<=-1))pasoR[temp_i]=0; if ((pasoG[temp_i]>=1)||(pasoG[temp_i]<=-1))pasoG[temp_i]=0; if ((pasoB[temp_i]>=1)||(pasoB[temp_i]<=-1))pasoB[temp_i]=0; } } } } break; } } } } long temp_level[12] = { 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095, 4095}; const char audio = '5'; const float attenua = 4; boolean stop_millis = false; void relampago(uint32_t time) { if ((time_millis>=time*factor)&&(ok_relampago)) { stop_millis = true; Serial.println("hola"); ok_relampago = false; // for (int canal=0; canal<12; canal++) temp_level[canal]=level[remap[canal]]; // for (int canal=0; canal<12; canal++) level[remap[canal]]=0; setGreys(); for(int x = 0; x < NUM_LEDS; ++x) strip.setPixelColor(x, 0, 0, 0); strip.show(); delay(10); // level[remap[3]]=4095; level[remap[8]]=0; level[remap[9]]=0; setGreys(); for (int value=4095; value>4095/attenua; value = value - 4) { level[remap[7]]=value; setGreys(); delayMicroseconds(2000); } for (int value=4095; value>200; value = value - 4) { level[remap[3]]=value; level[remap[4]]=value; level[remap[7]]=value/attenua; setGreys(); delayMicroseconds(2000); } for (int value=200; value>=0; value = value - 4) { level[remap[4]]=value; setGreys(); delayMicroseconds(2000); } delay(1000); while (Serial1.available()) Serial1.read(); boolean flag_ok = true; int retry = 0; while ((retry<5)&&(flag_ok)) { Serial1.print(audio); delay(100); unsigned long time_escape = time_millis; while (!Serial1.available()&&((time_millis-time_escape)<1000)); // while (!Serial1.available()); delay(100); while (Serial1.available()) { byte temp = Serial1.read(); Serial.write(temp); if (temp=='#') flag_ok = false; } retry++; // if (Serial1.read()=='#'); } while (flag_ok==false) { delay(1000); for(int x = 0; x < NUM_LEDS; ++x) strip.setPixelColor(x, 255, 255, 255); strip.show(); delay(100); for(int x = 0; x < NUM_LEDS; ++x) strip.setPixelColor(x, 0, 0, 0); strip.show(); delay(2000); for (int value=200; value<4095; value = value + 4) { level[remap[3]]=value; //level[remap[4]]=value; level[remap[7]]=value/attenua; setGreys(); delayMicroseconds(3000); } delay(14000); for (int value=4095; value>200; value = value - 4) { level[remap[3]]=value; //level[remap[4]]=value; level[remap[7]]=value/attenua; setGreys(); delayMicroseconds(2000); } for(int x = 0; x < NUM_LEDS; ++x) strip.setPixelColor(x, 255, 255, 255); strip.show(); delay(100); for(int x = 0; x < NUM_LEDS; ++x) strip.setPixelColor(x, 0, 0, 0); strip.show(); delay(2000); for (int value=200; value<4095; value = value + 4) { level[remap[3]]=value; level[remap[7]]=value/attenua; setGreys(); // feedPorts(); delayMicroseconds(2000); } // delay(6000); // int x = random(0, NUM_LEDS); // int time = random(10, 100); // strip.setPixelColor(x, 255, 255, 255); // strip.show(); // delay(time); // strip.setPixelColor(x, 0, 0, 0); // strip.show(); // delay(time); while (!Serial1.available());//feedPorts();; while (Serial1.available()) { byte temp = Serial1.read(); if (temp==audio) { flag_ok=true; Serial.println("OK"); // digitalWrite(CTS, LOW); // delay(1000); // digitalWrite(CTS, HIGH); } } for (int value=0; value<4095; value = value + 2) { level[remap[4]]=value; if (value<(4095/attenua)) level[remap[7]]=4095/attenua; else level[remap[7]]=value; setGreys(); // feedPorts(); delayMicroseconds(4000); } stop_millis = false; } // Serial.println((millis()-time_total[canal])); } const int incr_millis = 10; #define RESOLUTION 65536 // Timer1 is 16 bit unsigned int pwmPeriod; unsigned char clockSelectBits; char oldSREG; // To hold Status void timer1SetPeriod(long microseconds) // AR modified for atomic access { long cycles = (F_CPU / 2000000) * microseconds; // the counter runs backwards after TOP, interrupt is at BOTTOM so divide microseconds by 2 if(cycles < RESOLUTION) clockSelectBits = _BV(CS10); // no prescale, full xtal else if((cycles >>= 3) < RESOLUTION) clockSelectBits = _BV(CS11); // prescale by /8 else if((cycles >>= 3) < RESOLUTION) clockSelectBits = _BV(CS11) | _BV(CS10); // prescale by /64 else if((cycles >>= 2) < RESOLUTION) clockSelectBits = _BV(CS12); // prescale by /256 else if((cycles >>= 2) < RESOLUTION) clockSelectBits = _BV(CS12) | _BV(CS10); // prescale by /1024 else cycles = RESOLUTION - 1, clockSelectBits = _BV(CS12) | _BV(CS10); // request was out of bounds, set as maximum oldSREG = SREG; cli(); // Disable interrupts for 16 bit register access ICR1 = pwmPeriod = cycles; // ICR1 is TOP in p & f correct pwm mode SREG = oldSREG; TCCR1B &= ~(_BV(CS10) | _BV(CS11) | _BV(CS12)); TCCR1B |= clockSelectBits; // reset clock select register, and starts the clock } void timer1Initialize() { TCCR1A = 0; // clear control register A TCCR1B = _BV(WGM13); // set mode 8: phase and frequency correct pwm, stop the timer timer1SetPeriod(incr_millis*1000); TIMSK1 = _BV(TOIE1); } void timer1Stop() { TCCR1B &= ~(_BV(CS10) | _BV(CS11) | _BV(CS12)); // clears all clock selects bits TIMSK1 &= ~(_BV(TOIE1)); } //The timer interrupt routine, which periodically interprets the serial commands ISR(TIMER1_OVF_vect) { // sei(); //Reenable global interrupts, otherwise serial commands will get dropped if (!stop_millis) time_millis = time_millis + incr_millis; feedPorts(); // makemagic(); // makemagic(); // makemagic(); // makemagic(); }