====== Code Arduino ====== A tester ([[http://antoine.villeret.free.fr/?p=719|source]]) :\\ * [[http://inotool.org/]] pour téléverser les programmes sur des Arduinos #!/bin/bash for arduino in /dev/ttyACM* ; do ino upload -m micro -p $arduino sleep 1 done ===== Arduino Chimères OSC ===== * Fichiers : {{:projets:chimeres-orchestra:code-arduino:chimeresorchestra-arduino-201702.zip|}} Réception des données via le protocole OSC. ++++ chimeres-osc | /* * Chimères Orchestra * ================= * Robots drummers in public space by Reson-nance Numérique * * Website: * http://reso-nance.org/chimeres-orchestra * * Setup: * Ethernet (OSC) > Ethernet Shield > Arduino MEGA > Power Shield MOSFETS > DC Motors * * Wiring: * Ethernet Shield Arduino MEGA Power Shield * =============== ============ ============ * 10 10 (53) * 11 11 (51) * 12 12 (50) * 13 13 (52) * 5V 5V * GND GND GND * 2 3 * 3 5 * 5 6 * 6 9 * 7 10 * 8 11 * * OSC message: * /arm Id (int 0-5), PWM (int 0-255), Delay (int 0-100) * */ #include #include #include #include "PwmMotor.h" // ---- NETWORK ---- // byte myIp[] = { 192, 168, 0, 105 }; // IP int serverPort = 9105; // Receive port byte myMac[] = { 0xED, 0xAD, 0xBE, 0xEF, 0xFE, 0xED }; // MAC address // 101 UDOO // 102 { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED } // 103 { 0xEE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED } // 104 { 0xDD, 0xAD, 0xBE, 0xEF, 0xFE, 0xED } // 105 { 0xED, 0xAD, 0xBE, 0xEF, 0xFE, 0xED } // 106 { 0xCD, 0xAD, 0xBE, 0xEF, 0xFE, 0xED } char oscmsg[]="/arm"; OSCServer server; // to receive messages // ---- CONFIGURATIONS ---- // const int PINS[] = {2,3,5,6,7,8}; // pins Mosfets Shield (for MEGA because Ethernet Shield use 10,11,12,13 pin and 4th pin for SD Card) const int TIME_MAX = 120; const int NB = 6; const int TEMPO = 10; // sampling tempo const boolean DEBUG = true; // ---- MOTORS --------- // int motor_id, motor_pwm, motor_time; PwmMotor motors[NB]; unsigned long current = 0; // ---- SETUP ----------- // void setup() { Ethernet.begin(myMac,myIp); server.begin(serverPort); server.addCallback(oscmsg, &get_osc); // callback function (receive) if (DEBUG) Serial.begin(38400); for (int i=0; i < NB; i++) { motors[i].init(PINS[i], TIME_MAX, DEBUG); } } // ---- PROGRAM ----------- // void loop() { // UPDATE TIME current = millis(); if(server.availableCheck()>0){ // alive } // MOTOR OFF for (int i=0; i < NB; i++) { if( motors[i].isOn() ) motors[i].off(current); } delay(TEMPO); } // Get OSC Message void get_osc(OSCMessage *_mes){ motor_id=_mes->getArgInt32(0); motor_pwm=_mes->getArgInt32(1); motor_time=_mes->getArgInt32(2); if (DEBUG) { Serial.print(motor_id); Serial.print(motor_pwm); Serial.println(motor_time); } // MOTOR ON if( motors[motor_id].isOn() == false ) motors[motor_id].on(current, motor_pwm, motor_time); } ++++ ===== Idem avec capteur de présence (série) ===== * Fichiers : {{:projets:chimeres-orchestra:code-arduino:chimeresorchestra_arduino_sensor_20161104.zip|}} ++++ chimeres_capteur | // Chimères Orchestra // Raspberry Pi > Pd > Serial > Arduino MEGA > MOSFETS // Digital sensor to activate #include "PwmMotor.h" // ---- CONFIGURATIONS ---- // int pins[] = {3,5,6,9,10,11}; // pins Shield Mosfets int time_max = 150; boolean DEBUG = false; // ---- VARIABLES --------- // int id, pwm, time; const int nb = 6; PwmMotor motors[nb]; unsigned long current = 0; unsigned long button_interval = 50; unsigned long button_previous = 0; int button_state = 0; int button_last_state = 0; int button_pin = 2; //2,4,7,8,12,13 // ---- PROGRAM ----------- // void setup() { Serial.begin(38400); for (int i; i < nb; i++) { motors[i].init(pins[i], time_max, DEBUG); } } void loop() { current = millis(); // Sensor if(current - button_previous > button_interval) { // sampling button_previous = current; button_state = digitalRead(button_pin); if (button_state != button_last_state) { // if the state has changed Serial.println(button_state); } button_last_state = button_state; } // ON while (Serial.available()) { id = Serial.parseInt(); pwm = Serial.parseInt(); time = Serial.parseInt(); if (Serial.read() == '\n') { if( motors[id].isOn() == false ) motors[id].on(current, pwm, time); } } // OFF for (int i; i < nb; i++) { if( motors[i].isOn() ) motors[i].off(current); } delay(5); } ++++ ===== Serial / Arduino / PwmMotor library ===== * Fichiers : {{:projets:chimeres-orchestra:code-arduino:chimeres_serial_interval_pwm.zip|}} ++++ chimeres_serial_interval_pwm | // Chimères Orchestra // Pd > Serial > Arduino MEGA > MOSFETS #include "PwmMotor.h" // ---- CONFIGURATIONS ---- // int pins[] = {2,3,4,5,6,7}; int time_max = 150; boolean DEBUG = false; // ---- VARIABLES --------- // int id, pwm, time; const int nb = 6; PwmMotor motors[nb]; unsigned long current = 0; // ---- PROGRAM ----------- // void setup() { Serial.begin(38400); for (int i; i < nb; i++) { motors[i].init(pins[i], time_max, DEBUG); } } void loop() { current = millis(); // ON while (Serial.available()) { id = Serial.parseInt(); pwm = Serial.parseInt(); time = Serial.parseInt(); if (Serial.read() == '\n') { if( !motors[id].isOn() ) motors[id].on(current, pwm, time); } } // OFF for (int i; i < nb; i++) { if( motors[i].isOn() ) motors[i].off(current); } delay(1); } ++++ ++++ PwmMotor.h | #ifndef PWMMOTOR_H #define PWMMOTOR_H #include class PwmMotor { public: PwmMotor(); ~PwmMotor(); void init(int _pin, int _time_max, boolean _debug); void on(unsigned long _current, int _pwm, int _time); void off(unsigned long _current); boolean isOn(); private: boolean debug; boolean state; unsigned long last; long time_on; int time_on_max; int pin; }; #endif ++++ ++++ PwmMotor.cpp | #include "PwmMotor.h" PwmMotor::PwmMotor(){ state = false; last = 0; time_on = 150; debug = false; } PwmMotor::~PwmMotor(){} void PwmMotor::init(int _pin, int _time_max, boolean _debug = false){ debug = _debug; time_on_max = _time_max; pin = _pin; pinMode(pin, OUTPUT); digitalWrite(pin, LOW); } boolean PwmMotor::isOn(){ return state; } void PwmMotor::on(unsigned long _current, int _pwm, int _time){ if( _current - last >= (time_on + 10) ) { // !state && state = true; last = _current; time_on = constrain(_time, 0, time_on_max); if (debug) Serial.println("ON "); analogWrite(pin, _pwm); } } void PwmMotor::off(unsigned long _current) { if( _current - last >= time_on ) { // state && state = false; analogWrite(pin, 0); if (debug) Serial.println("OFF"); } } ++++ ===== UDP / OSC ===== ++++ Code UDP OSC | #include #include boolean DEBUG = false; int pins_pwm[] = {2,3,4,5,6,7}; int pins_nb = 6; byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED }; IPAddress ip(192, 168, 0, 102); unsigned int localPort = 8888; char packetBuffer[UDP_TX_PACKET_MAX_SIZE]; char *inParse[100]; EthernetUDP Udp; void setup() { Ethernet.begin(mac,ip); Udp.begin(localPort); if (DEBUG) Serial.begin(38400); for (int thisPin = 0; thisPin < pins_nb ; thisPin++) { pinMode(thisPin, OUTPUT); digitalWrite(thisPin, LOW); } } void loop() { int packetSize = Udp.parsePacket(); if(packetSize) { Udp.read(packetBuffer,UDP_TX_PACKET_MAX_SIZE); //if (DEBUG) Serial.println(packetBuffer); ParseData(); } delay(1); } void ParseData() { char *p = packetBuffer; char *str; String func; int count = 0; // delimiter " " while ((str = strtok_r(p, " ", &p)) != NULL) { inParse[count] = str; count++; //if (DEBUG) Serial.println(str); } if(count == 3) { func = inParse[0]; if (func == "/pwm") { int tmpPin = atoi(inParse[1]); int tmpPwm = atoi(inParse[2]); analogWrite(pins_pwm[tmpPin], constrain(tmpPwm,0,255)); if (DEBUG) Serial.println(inParse[1]); if (DEBUG) Serial.println(inParse[2]); } } } ++++ ===== SERIAL - UNO ===== ++++ Code UNO / PWM | /* * Pd > Arduino UNO * 6 sorties MOSFETS PWM * */ int pin, _pwm; void setup() { Serial.begin(19200); pinMode(3, OUTPUT); pinMode(5, OUTPUT); pinMode(6, OUTPUT); pinMode(9, OUTPUT); pinMode(10, OUTPUT); pinMode(11, OUTPUT); digitalWrite(3, LOW); digitalWrite(5, LOW); digitalWrite(6, LOW); digitalWrite(9, LOW); digitalWrite(10, LOW); digitalWrite(11, LOW); // --- PWM frequency for D5 & D6 ---- //TCCR0B = TCCR0B & B11111000 | B00000001; // 62500.00 Hz //TCCR0B = TCCR0B & B11111000 | B00000010; // 7812.50 Hz //TCCR0B = TCCR0B & B11111000 | B00000011; // 976.56 Hz //TCCR0B = TCCR0B & B11111000 | B00000100; // 244.14 Hz //TCCR0B = TCCR0B & B11111000 | B00000101; // 61.04 Hz // ---- PWM frequency for D9 & D10 ---- //TCCR1B = TCCR1B & B11111000 | B00000001; // 31372.55 Hz //TCCR1B = TCCR1B & B11111000 | B00000010; // 3921.16 Hz //TCCR1B = TCCR1B & B11111000 | B00000011; // 490.20 Hz //TCCR1B = TCCR1B & B11111000 | B00000100; // 122.55 Hz //TCCR1B = TCCR1B & B11111000 | B00000101; // 30.64 Hz // ---- PWM frequency for D3 & D11 ---- //TCCR2B = TCCR2B & B11111000 | B00000001; // 31372.55 Hz //TCCR2B = TCCR2B & B11111000 | B00000010; // 3921.16 Hz //TCCR2B = TCCR2B & B11111000 | B00000011; // 980.39 Hz //TCCR2B = TCCR2B & B11111000 | B00000100; // 490.20 Hz //TCCR2B = TCCR2B & B11111000 | B00000101; // 245.10 Hz //TCCR2B = TCCR2B & B11111000 | B00000110; // 122.55 Hz //TCCR2B = TCCR2B & B11111000 | B00000111; // 30.64 Hz } void loop() { while (Serial.available()) { pin = Serial.parseInt(); _pwm = Serial.parseInt(); if (Serial.read() == '\n') { /* Serial.print(pin); Serial.print(" "); Serial.println(_pwm); */ analogWrite(pin, constrain(_pwm,0,255)); } } } ++++ ===== SERIAL - MEGA ===== ++++ Code Mega / PWM | // Pd > Arduino MEGA // 6 sorties MOSFETS PWM int id; int arg; void setup() { Serial.begin(19200); pinMode(13, OUTPUT); pinMode(12, OUTPUT); pinMode(11, OUTPUT); pinMode(10, OUTPUT); pinMode(9, OUTPUT); pinMode(8, OUTPUT); digitalWrite(13, LOW); digitalWrite(12, LOW); digitalWrite(11, LOW); digitalWrite(10, LOW); digitalWrite(9, LOW); digitalWrite(8, LOW); //MEGA : D4 & D13 //TCCR0B = TCCR0B & B11111000 | B00000001; // 62500.00 Hz //TCCR0B = TCCR0B & B11111000 | B00000010; // 7812.50 Hz //TCCR0B = TCCR0B & B11111000 | B00000011; // 976.56 Hz //TCCR0B = TCCR0B & B11111000 | B00000100; // 244.14 Hz //TCCR0B = TCCR0B & B11111000 | B00000101; // 61.04 Hz //MEGA : D11 & D12 //TCCR1B = TCCR1B & B11111000 | B00000001; //31372.55 Hz //TCCR1B = TCCR1B & B11111000 | B00000010; //3921.16 Hz //TCCR1B = TCCR1B & B11111000 | B00000011; //490.20 Hz //TCCR1B = TCCR1B & B11111000 | B00000100; //122.55 Hz //TCCR1B = TCCR1B & B11111000 | B00000101; //30.64 Hz //MEGA : D9 & D10 //TCCR2B = TCCR2B & B11111000 | B00000001; //31372.55 Hz //TCCR2B = TCCR2B & B11111000 | B00000010; //3921.16 Hz //TCCR2B = TCCR2B & B11111000 | B00000011; //490.20 Hz //TCCR2B = TCCR2B & B11111000 | B00000100; //122.55 Hz //TCCR2B = TCCR2B & B11111000 | B00000101; //30.64 Hz //MEGA : D2, D3 & D5 //TCCR3B = TCCR3B & B11111000 | B00000001; //31372.55 Hz //TCCR3B = TCCR3B & B11111000 | B00000010; //3921.16 Hz //TCCR3B = TCCR3B & B11111000 | B00000011; //490.20 Hz //TCCR3B = TCCR3B & B11111000 | B00000100; //122.55 Hz //TCCR3B = TCCR3B & B11111000 | B00000101; //30.64 Hz //MEGA : D6, D7 & D8 //TCCR4B = TCCR4B & B11111000 | B00000001; //31372.55 Hz //TCCR4B = TCCR4B & B11111000 | B00000010; //3921.16 Hz //TCCR4B = TCCR4B & B11111000 | B00000011; //490.20 Hz //TCCR4B = TCCR4B & B11111000 | B00000100; //122.55 Hz //TCCR4B = TCCR4B & B11111000 | B00000101; //30.64 Hz //MEGA : D44, D45 & D46 //TCCR5B = TCCR5B & B11111000 | B00000001; //31372.55 Hz //TCCR5B = TCCR5B & B11111000 | B00000010; //3921.16 Hz //TCCR5B = TCCR5B & B11111000 | B00000011; //490.20 Hz //TCCR5B = TCCR5B & B11111000 | B00000100; //122.55 Hz //TCCR5B = TCCR5B & B11111000 | B00000101; //30.64 Hz } void loop() { while (Serial.available()) { id = Serial.parseInt(); arg = Serial.parseInt(); if (Serial.read() == '\n') { /* Serial.print("CMD : "); Serial.print(id); Serial.print(" "); Serial.println(arg); */ analogWrite(id, constrain(arg,0,255)); } } } ++++ ===== Dublin 06/2012 ===== * Code répéteur autonome (avec piezo) * Fichiers : {{:projets:chimeres-orchestra:code-arduino:chimeresorchestra_0_04.zip|}} ++++ Code autonome | // Not tested ! // TO DO : verify input sensor and automatic, verify sequences modes // ******************************************* // // Chimères Orchestra // Robotic drums in public space // In the "Hack the city" exhibition, Science Gallery, Dublin // http://jeromeabel.net/art/chimeres-orchestra // Jérome Abel - 22/06/2012 // GNU/GPL v3 // ******************************************* // // LIEU // 0 : Gallery, 1 : Meeting house square (left side), 2 : Meeting house square (right side) int LOCATION = 0; // SOLENOIDS const int NUMBER = 5; int solenoids_pins [][NUMBER] = { {5,2,7,6,8}, // Gallery {4,6,8,12,5}, // Meeting house square (left side) {4,6,12,7,5}, // Meeting house square (right side) }; // DEBUG boolean DEBUG = true; // AUTOMATIC TIME //int auto_interval = 15*60000; // 15 minutes int auto_interval = 20000; // 15 minutes int auto_duration = 5000; // PIEZO const int p_threshold = 80; const int p_debounce = 100; // antirebond const int p_interval = 12000; // after 8 seconds, rhythms stop const int p_interval_min = 8000; // minimum const int p_interval_max = 25000; // maximum const int p_declenchement_seq = 8; // number of hits to start rhythms const int p_pin = A0; // sensor pin // ATTACK TIME int on = 35; // default setting int s_attack_on = on; // default setting int s_attack_on_min = 30; int s_attack_on_max = 45; int off = 90;// default setting int s_attack_off = off ; int s_attack_off_min = 80; int s_attack_off_max = 110; int seq_interval = s_attack_on + s_attack_off; // ******************* RHYTHMS ********************* // // SEQUENCES boolean seq[][4] = { {0,0,0,0}, // 0 {1,0,0,0}, // 1 {0,1,0,0}, // 2 {0,0,1,0}, // 3 {0,0,0,1}, // 4 {1,1,0,0}, // 5 {1,0,1,0}, // 6 {1,0,0,1}, // 7 {0,1,1,0}, // 8 {0,1,0,1}, // 9 {0,0,1,1}, // 10 {1,1,1,0}, // 11 {0,1,1,1}, // 12 {1,1,1,1} // 13 }; int patterns[][4] = { {5,5,5,5}, //0 {4,4,4,12}, {0,1,1,1}, {1,1,1,1}, {1,1,1,2}, {2,2,3,2}, {3,3,3,3}, {4,4,4,4}, {7,5,5,5}, {5,5,5,0}, {3,5,3,5}, {1,7,1,7}, {0,12,0,13}, {4,5,4,0}, {9,9,4,9}, {2,6,6,2}, {7,1,7,1}, {12,0,12,0}, {13,13,13,0}, // 18 // EXTRA {12,0,0,0}, // 19 {0,0,0,5}, {0,0,0,9}, {2,5,0,0}, {0,3,0,3}, {3,0,5,0}, {6,6,0,0}, {0,0,0,13}, {0,0,0,8}, {0,0,0,11}, {0,0,12,0}, {0,1,0,1}, {0,0,1,1}, {0,1,1,0}, {2,0,2,0}, {0,0,2,5}, {1,0,11,0}, {0,13,11,0} //36 }; // *************************************************** // int seq_counter = 0; int seq_counter_pattern = 0; int seq_tempo = 0; int solenoids_seq[6]; boolean auto_sequence = false; int sequence_mode = 0; // TIME unsigned long currentMillis = 0; unsigned long previousMillis = 0; int interval = 1000; unsigned long auto_time = 0; // TAP TEMPO unsigned long p_taptempo = 0; float p_taptempo_average = 0; float p_taptempo_total = 0; float p_last_taptempo = 0; // PIEZO int p_reading = 0; boolean p_state = false; boolean p_state_last = false; long p_time = 0; int p_counter = 0; long p_counter_time = 0; // SEQUENCE long alternate_time = 0; int random_seq = random(24,32); int random_attack_time = random(16,32); // ****************** getPiezo() ************************* // boolean getPiezo(){ p_reading = analogRead(p_pin); if (p_reading >= p_threshold && currentMillis - p_time >= p_debounce) { p_counter++; if (DEBUG) { Serial.println("============"); Serial.println("Knock!"); Serial.print("PIEZO COUNTER:"); Serial.println(p_counter); } if (p_counter > 1) { p_last_taptempo = p_taptempo; p_taptempo = currentMillis - p_time; if (DEBUG) { Serial.print("TAPTEMPO:"); Serial.println(p_taptempo); } p_taptempo_total = (int)p_taptempo + (int)p_last_taptempo; if (p_counter > 2) { p_taptempo_average = p_taptempo_total / 2 ; if (DEBUG) { Serial.print("AVERAGE:"); Serial.println(p_taptempo_average); } } } p_time = currentMillis; return true; } else { return false;} } // ***************** single_attack() **************** // void single_attack(int pin){ digitalWrite(pin, HIGH); delay(s_attack_on); digitalWrite(pin, LOW); delay(s_attack_off); } // ****************** chenillard() ****************** // void chenillard(){ if (DEBUG) Serial.println("CHENILLARD"); for (int i = 0; i < NUMBER ; i++) { single_attack(solenoids_pins[LOCATION][i]); delay(250); } } // ****************** SETUP ************************* // void setup() { randomSeed(analogRead(1)); Serial.begin(9600); for (int i = 0; i < NUMBER ; i++) { pinMode(solenoids_pins[LOCATION][i], OUTPUT); solenoids_seq[i] = random(13); } delay(1000); chenillard(); } // ****************** LOOP ************************* // void loop() { currentMillis = millis(); // start automatic if (currentMillis - auto_time > auto_interval){ auto_sequence = true; sequence_mode = 1;//random(2); auto_time = currentMillis; seq_counter_pattern=0; seq_counter=0; if (DEBUG) Serial.println("AUTO:ON"); } // stop automatic if (auto_sequence && currentMillis - auto_time > auto_duration){ auto_sequence = false; if (DEBUG) Serial.println("AUTO:OFF"); } // getPiezo // if (!auto_sequence) p_state = getPiezo(); // p_interval, counter if (!auto_sequence && currentMillis - p_time > p_interval ){ p_counter=0; p_taptempo_total = 0; p_taptempo_average = 0; seq_counter=0; seq_counter_pattern=0; } // single_attack with the piezo if (p_counter > 0 && p_counter < p_declenchement_seq && p_state) { int pin = solenoids_pins[LOCATION][random(NUMBER)]; if (DEBUG) { Serial.print("ATTACK PIN:"); Serial.println(pin); } single_attack(pin); } // start rhythms with a "chenillard" if (p_counter == p_declenchement_seq) { chenillard(); sequence_mode = random(2); } if (p_counter >= p_declenchement_seq || auto_sequence ) { if (!auto_sequence) seq_tempo = seq_interval * (p_taptempo_average / 1000); // change the tempo with piezo tap tempo else seq_tempo = seq_interval; if (currentMillis - previousMillis > seq_tempo ) { if (DEBUG) { Serial.print("SEQ COUNTER :"); Serial.println(seq_counter); } // random attack time on/off every [8-32] steps if (seq_counter % random_attack_time == 0) { random_attack_time = random(8,32); if (random(100) > 60) { // 40% of random s_attack_on = random (s_attack_on_min, s_attack_on_max); s_attack_off = random (s_attack_off_min, s_attack_off_max); } else { s_attack_on = on; s_attack_on = off; } seq_interval = s_attack_on + s_attack_off; // update sequence interval } // SEQUENCE MODE 0 (random) if (sequence_mode == 0) { // random sequences every [24-32] steps if (seq_counter % random_seq == 0) { random_seq = random(24,32); for (int i = random(2); i < random(4,6) ; i++) { solenoids_seq[i] = random(14); } } // ON : sequences for each pins for (int i = 0; i < NUMBER ; i++) { digitalWrite(solenoids_pins[LOCATION][i], seq[solenoids_seq[i]][seq_counter % 4]); } delay(s_attack_on); } // SEQUENCE MODE 1 (less random, more human) if (sequence_mode == 1) { // random patterns every [24-32] steps if (seq_counter % random_seq == 0) { random_seq = random(32,64); for (int i = random(2); i < random(4,6) ; i++) { int choice = random(3); if (choice == 0) solenoids_seq[i] = random(19); else if (choice == 1) solenoids_seq[i] = random(19,36); } } // ON : sequences for each pins for (int i = 0; i < NUMBER ; i++) { digitalWrite(solenoids_pins[LOCATION][i], seq[patterns[solenoids_seq[i]][seq_counter_pattern % 4]][seq_counter % 4]); if (DEBUG) { Serial.println ("=========="); Serial.print ("INDEX"); Serial.print (i); Serial.print (" - SOLENOID : "); Serial.print (solenoids_pins[LOCATION][i]); Serial.print (" - PATTERN :"); Serial.print (solenoids_seq[i]); Serial.print (" - SEQ : "); Serial.print (patterns[solenoids_seq[i]][seq_counter_pattern % 4]); Serial.print (" - DIGITAL WRITE: "); Serial.println (seq[patterns[solenoids_seq[i]][seq_counter_pattern % 4]][seq_counter % 4]); } if (seq_counter % 4 == 0) { seq_counter_pattern++; } } delay(s_attack_on); } // OFF : all off for (int i = 0; i < NUMBER ; i++) { digitalWrite(solenoids_pins[LOCATION][i], 0); } delay(s_attack_off); seq_counter++; previousMillis = currentMillis; } // end seq_tempo } // end start rythms delay(5); // delay to avoid overloading the serial port buffer } ++++