Final Project Post: In My Corner

on

In My Corner

At the Maker Faire

In My Corner is a project that I made for the class. The major components consist of a wooden frame, 4 servo motors, 2 Arduinos, a microphone, a roll of paper, an audio interface to amplify the microphone, an RC motor to control the roll of paper, a ping))) sensor, and two markers.

Without the paper

The purpose of this project was to create a machine that would record sound and distance to the machine and display it. This was meant to show the “emotions” of the machine and also served as a visual representation of the way people interacted with the machine. As people got closer to the machine and as the room became louder, the machine would draw lines with a bigger amplitude.

Code: drawingByDistance

/**
drawingByDistance
Author: Carlos Ortega
This code is used to move two motors at the same time using the distance measured by the PING))) sensor
We also have three butons that are used for calibration.
*/
#include <Servo.h>
//the pins that correspond to the buttons
const int leftButton = 2;
const int rightButton = 3;
const int stopButton = 4;
//the pin that corresponds to the PING)))
const int pingPin =7;
const int maxDist = 70; //in inches
const int minDist = 30;  //also in inches
//servo vars
Servo myservo;
int leftOrRight = -1; //-1 = left, 1=right
const int maxDrawTime = 800; //max time for each line in millisecs. 
                              //this corresponds to the max amplitude of the line
//vars for buttons
int leftState = 0;
int rightState = 0;
int start = -1;
int startStatus = 0;
//vars for PING)))
long pingTime = 0.0;
int inchDistance = 0;
void setup(){
  myservo.attach(9);  //attaches the servo to the pwm in pin 9
  pinMode(leftButton, INPUT);  //initialize the push button as inputs
  pinMode(rightButton, INPUT);
  pinMode(stopButton, INPUT);
  
//  //debug stuff
//  Serial.begin(9600);
}
void loop(){
  leftState = digitalRead(leftButton);
  rightState = digitalRead(rightButton);
  startStatus = digitalRead(stopButton);
  
  if(startStatus == HIGH)
    start = start*-1;
  
  //Do normal routine of checking distance and what not  
  if( start > 0 ){
    //debugggg life
    Serial.println(“in normal”);
    
    //Pulse out
    pinMode(pingPin, OUTPUT);
    digitalWrite(pingPin, LOW);
    delayMicroseconds(2);
    digitalWrite(pingPin, HIGH);
    delayMicroseconds(5);
    digitalWrite(pingPin, LOW);
    
    //read pulse back
    pinMode(pingPin, INPUT);
    pingTime = pulseIn(pingPin, HIGH);
    
    //convert that s**t to inches and cast it as an int yeah! and constrain it and then map it
    inchDistance = constrain( (int) timeToInches(pingTime), minDist, maxDist);
    inchDistance = map(inchDistance, minDist, maxDist, maxDrawTime, 0);
    
    inchDistance = inchDistance – inchDistance%100;
    
    //More debug things
    Serial.println(inchDistance);
   
    if(inchDistance >= 100){
      
//      //debug stuff dont pay attention
//      Serial.println(“i shouldnt be here!”);
      
      //move those motors
      moveMotors(inchDistance);
      delay(100);
    }
  }
  
  //manual movements using the buttons used for calibration
  else if ( start < 0){
     
//     //More debug, not important   
//     Serial.println(“in calib”);
//     Serial.println(start);  
    
     //turn left
     if(leftState == HIGH && rightState == LOW){
       myservo.writeMicroseconds(1300);    //turn motor clockwise
       delay(100);
       myservo.writeMicroseconds(1500);    //stop
       
//       //Deeeebug stuff!
//       Serial.println(“left”);
     }
     //turn right
     else if(leftState == LOW && rightState == HIGH){
       myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
       delay(100);
       myservo.writeMicroseconds(1500);    //stop
       
//       //deeeeeeeeeebug!
//       Serial.println(“right”);
     }
  }
  
}//end of loop()
//taken directly from the Ping example on:http://www.arduino.cc/en/Tutorial/Ping
//because it makes my life esier
long timeToInches(long microsecs){
  // According to Parallax’s datasheet for the PING))), there are
  // 73.746 microseconds per inch (i.e. sound travels at 1130 feet per
  // second).  This gives the distance travelled by the ping, outbound
  // and return, so we divide by 2 to get the distance of the obstacle.
  // See: http://www.parallax.com/dl/docs/prod/acc/28015-PING-v1.3.pdf
  return microsecs / 74 / 2;
}
void moveMotors(int time){
  // go left
  if(leftOrRight < 0){
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    
    for(int x =0; x< time; x++){
      if(digitalRead(rightButton) == 1){
        returnToCenter(1);
        //update leftOrRight
        leftOrRight = leftOrRight * -1;
        return;
      }
      delay(1);
    }
    myservo.writeMicroseconds(1500);    //stop
    
    delay(100);
    
    //return to original pos
    myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
    delay(time);
    myservo.writeMicroseconds(1500);    //stop
  }
  
  //go right
  else if(leftOrRight > 0){
    myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
    
    for(int x = 0; x < time; x++){
      if(digitalRead(leftButton) == 1){
        returnToCenter(-1);
        //update leftOrRight
        leftOrRight = leftOrRight * -1;
        return;
      }
      delay(1);
    }
    myservo.writeMicroseconds(1500);    //stop
    
    delay(100);
    
    //return to original position
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    delay(time);
    myservo.writeMicroseconds(1500);    //stop
  }
  
  //update leftOrRight
  leftOrRight = leftOrRight * -1;
  
//  //More debug, not important
//  Serial.println(leftOrRight);
//  Serial.println(time);
}
void returnToCenter(int goLR){
  //go left
  if(goLR < 0){
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    delay(maxDrawTime);
    myservo.writeMicroseconds(1500);    //stop
  }
  else if(goLR > 0){
    myservo.writeMicroseconds(1700);    //turn motor clockwise
    delay(maxDrawTime);
    myservo.writeMicroseconds(1500);    //stop
  }
}

Code: drawingByNoise

/**
  drawingByNoise
  Author: Carlos Ortega
  
  This code is used to control two motors based in the input from a mic
  We also have three buttons used for calibration
*/
#include <Servo.h>
//the pins that correspond to the buttons
const int leftButton = 2;
const int rightButton = 3;
const int stopButton = 4;
//servo vars
Servo myservo;
int leftOrRight = -1; //-1 = left, 1=right
int maxDrawTime = 1150; //max time for each line in millisecs. 
                              //this corresponds to the max amplitude of the line
                              
int sensorPin = A0;    // select the input pin for the mic
int volume = 0;        // variable to store the volume level value coming from the sensor
int delayTime = 100;
//vars used for volume array
const int arraySize = 50;
int count = 0;
int average = 0;
int readVals[arraySize];
int lowTresh = 0;
int midTresh = 0;
int highTresh = 0;
int higherTresh = 0;
float percentDiff = .50;
//vars for buttons
int leftState = 0;
int rightState = 0;
int start = -1;
int startStatus = 0;
void setup() {
  Serial.begin(9600);
  myservo.attach(9);              //attaches the servo to the pwm in pin 9
  pinMode(leftButton, INPUT);     //initialize the push button as inputs
  pinMode(rightButton, INPUT);
  pinMode(stopButton, INPUT); 
  
  for (int x = 0; x < arraySize; x++)
    readVals[x] = volume = analogRead(sensorPin);
}
void loop() {
  
  leftState = digitalRead(leftButton);
  rightState = digitalRead(rightButton);
  startStatus = digitalRead(stopButton);
  
  if(startStatus == HIGH)
    start = start*-1;
  
  //manual movements using the buttons used for calibration
  if ( start < 0){
      
     //turn left
     if(leftState == HIGH && rightState == LOW){
       myservo.writeMicroseconds(1300);    //turn motor clockwise
       delay(100);
       myservo.writeMicroseconds(1500);    //stop
     }
     //turn right
     else if(leftState == LOW && rightState == HIGH){
       myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
       delay(100);
       myservo.writeMicroseconds(1500);    //stop
     }
  }
  
  else if(start > 0){
  
   //store val into the array
   if(count >= arraySize)
     count = 0;
   
   readVals[count] = analogRead(sensorPin); 
   count ++;
   
   //get average
   int sum = 0;
   for(int x = 0; x < arraySize; x++){
     sum = readVals[x] + sum;
   }
   average = sum/arraySize;
   
   volume = 0;
   for(int x = 0; x < arraySize; x++)
     volume = volume + analogRead(sensorPin);
   volume = volume/(arraySize);
   
   if(volume > average){
     for (int x = 0; x < arraySize; x++)
       readVals[x] = volume = analogRead(sensorPin);
      
      sum = 0;
      for(int x = 0; x < arraySize; x++){
        sum = readVals[x] + sum;
      }
      average = sum/arraySize;
   }
  
   lowTresh = average * (1 + (percentDiff * 1));
   midTresh = average * (1 + (percentDiff * 2));
   highTresh = average * (1 + (percentDiff * 3));
   higherTresh = average * (1 + (percentDiff * 4));
   
   volume = 0;
   for(int x = 0; x < 50; x++)
     volume = volume + analogRead(sensorPin);
   volume = volume/(20);
   
   if(volume <= lowTresh){
     Serial.println(“Here1”);
   }
   else if(volume > lowTresh && volume < midTresh && midTresh != 0){
     moveMotors(maxDrawTime/4);
     Serial.println(“here2”);
   }
   else if(volume >= midTresh && volume < highTresh && (midTresh-highTresh)!= 0){
     moveMotors(maxDrawTime/2);
     Serial.println(“here3”);
   }
   else if(volume >= highTresh && volume < higherTresh && highTresh != 0){
     moveMotors((maxDrawTime*3)/4);
     Serial.println(“here4”);    
   }
   else if(volume >= higherTresh && higherTresh != 0){
     moveMotors(maxDrawTime);
     Serial.println(“here5”);    
   }     
   
   Serial.print(average);  
   Serial.print(“t”); //prints a tab
   Serial.print(“t”); //prints a tab
   Serial.print(volume);  
   Serial.print(“t”); //prints a tab
   Serial.print(“t”); //prints a tab
   Serial.print(lowTresh);
   Serial.print(“t”); //prints a tab
   Serial.print(“t”); //prints a tab
   Serial.print(midTresh);
   Serial.print(“t”); //prints a tab
   Serial.print(“t”); //prints a tab
   Serial.print(highTresh);
   Serial.println(maxDrawTime + ” HELLLOOOO”);
   delay(delayTime);
  }
}
void moveMotors(int time){
  // go left
  if(leftOrRight < 0){
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    
    for(int x =0; x< time; x++){
      if(digitalRead(rightButton) == 1){
        returnToCenter(1);
        //update leftOrRight
        leftOrRight = leftOrRight * -1;
        return;
      }
      delay(1);
    }
    myservo.writeMicroseconds(1500);    //stop
    
    delay(100);
    
    //return to original pos
    myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
    delay(time);
    myservo.writeMicroseconds(1500);    //stop
  }
  
  //go right
  else if(leftOrRight > 0){
    myservo.writeMicroseconds(1700);    //turn motor counter-clockwise
    
    for(int x = 0; x < time; x++){
      if(digitalRead(leftButton) == 1){
        returnToCenter(-1);
        //update leftOrRight
        leftOrRight = leftOrRight * -1;
        return;
      }
      delay(1);
    }
    myservo.writeMicroseconds(1500);    //stop
    
    delay(100);
    
    //return to original position
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    delay(time);
    myservo.writeMicroseconds(1500);    //stop
  }
  
  //update leftOrRight
  leftOrRight = leftOrRight * -1;
  
//  //More debug, not important
//  Serial.println(leftOrRight);
//  Serial.println(time);
}
void returnToCenter(int goLR){
  //go left
  if(goLR < 0){
    myservo.writeMicroseconds(1300);    //turn motor clockwise
    delay(maxDrawTime);
    myservo.writeMicroseconds(1500);    //stop
  }
  else if(goLR > 0){
    myservo.writeMicroseconds(1700);    //turn motor clockwise
    delay(maxDrawTime);
    myservo.writeMicroseconds(1500);    //stop
  }
}