Skip to content

Instantly share code, notes, and snippets.

@stoefln
Last active February 4, 2017 09:06
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save stoefln/9ad571830b042fe70185ada6736c4337 to your computer and use it in GitHub Desktop.
Save stoefln/9ad571830b042fe70185ada6736c4337 to your computer and use it in GitHub Desktop.
/*
* Arduino control for a solenoid valve array (currently 8 pieces), which are hooked up to tubes with liquid inside.
* Each solenoid valve controls a stream of air which is blown into the stream of liquid inside the tubes.
* By layouting the tubes on a wall it's possible to create beautiful animations
*/
#define TRACK_NUMBER 8
#define MAX_CHARS_PER_TRACK 80
class Track
{
private:
unsigned long lastUpdate=0;
int step = 0;
int pin;
float speed = 30;
int notesPerBeat;
const char* pattern;
public:
Track(){
Serial.println("init new empty track");
}
// speed: bpm / 16
void loadPattern(const char* pattern) {
this->pattern = pattern;
this->notesPerBeat = strlen(pattern);
Serial.print("load pattern pin");
Serial.print(this->pin);
Serial.print(": ");
Serial.print(this->pattern);
Serial.print("size: ");
Serial.println(this->notesPerBeat);
}
long getLastUpdate(){
return lastUpdate;
}
void setSpeed(int speed) {
this->speed = speed;
}
void setPin(int pin) {
this->pin = pin;
}
const char * getPattern(){
return this->pattern;
}
void update(){
int timePerStep = (int) (10000.0 / (float) speed);
if(this->lastUpdate + timePerStep < millis()){
char onOff = pattern[step];
if(onOff == 'x'){
digitalWrite(pin, HIGH);
}else{
if(pin == 4 || pin == 11){
Serial.print(step);
Serial.print("th step ");
Serial.print(pin);
Serial.print(" off ");
Serial.print(" onOff:");
//Serial.println((int) onOff);
}
digitalWrite(pin, LOW);
}
lastUpdate = millis();
step++;
if(step >= notesPerBeat){
step = 0;
}
}
}
};
class Sequencer {
Track tracks[TRACK_NUMBER];
public:
Sequencer(){}
void init(int pins[], int speed){
for(int i=0;i<TRACK_NUMBER;i++){
int pin = pins[i];
Serial.print("create new track on pin ");
Serial.println(pin);
//this->tracks[i] = Track(pin);
tracks[i].setPin(pin);
tracks[i].setSpeed(speed);
}
}
void loadPattern(const char pattern[][MAX_CHARS_PER_TRACK]){
for(int i=0;i<TRACK_NUMBER;i++) {
tracks[i].loadPattern(pattern[i]);
}
}
Track getTrack(int pos){
return tracks[pos];
}
void setSpeed(int speed){
for(int i=0;i<TRACK_NUMBER;i++) {
tracks[i].setSpeed(speed);
}
}
void update(){
for(int i=0;i<TRACK_NUMBER;i++) {
tracks[i].update();
}
}
};
Sequencer sequencer;
void setup() {
Serial.begin(9600);
int pins[] = {11, 10, 9, 8, 7, 6, 5, 4};
const char pattern2[TRACK_NUMBER][MAX_CHARS_PER_TRACK] =
{" xxxx xxxx xx x x ",
" x x ",
" x x ",
" x x ",
" x x ",
" x x ",
" x x ",
" xxxx xxxx xx x x ",
};
sequencer.init(pins, 120);
sequencer.loadPattern(pattern2);
Serial.println("pattern after setup (still OK): ");
Serial.println(sequencer.getTrack(7).getPattern());
}
void loop() {
Serial.println("pattern before update (still ok): ");
Serial.println(sequencer.getTrack(7).getPattern()); // <-- prints " xxxx xxxx xx x x "
sequencer.update(); // <-- this is where some memory issue is happening, screwing up the pattern2 var
Serial.println("pattern after update (messed up): ");
Serial.println(sequencer.getTrack(7).getPattern()); // <-- prints " xxxx xx���4"
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment