Please direct any design or CAD questions to Thanos: [email protected]
// Ngai To Lo, Thanos Kritharis
// Build 1.5 Refactor: Siang Lim
/* Regionals 2017 Build 1.5
/* sensor design is LDR */
/* valve control is solenoid valve*/
//initiating digital pins
#define WHEELDIAMETER 15.18 // Actual wheel (not encoder wheel) diameter in cm
#define ENCODERRESOLUTION 60.0 // Number of teeth on the encoder wheel
#define DARKPOINTSTHRESHOLD 20 // Threshold for number of dark points for triggering the clock
#define REPORTTIME 5000 // Interval to print values to mobile app
#define MIXERSPEED 28 // Equation is V=(X/256)*5, where X is a value between 1-256 (How fast the mixer spins)
#define DLDR 60 // Clock sensitivity: Change in reference value required to trigger clock
#define BUTTONPRESSED 1 //Value to indicate that button is pressed
int ldrRef = 995; //Reference value average
int ldrRefl = 1000; //Reference value for sensor lower
int ldrRefu = 1005; //Reference vallue for sensor upper
int encoderSensor = 2; //Pin used to measure optosensor input
int startButton = 7; //Pin used to control startup (Input)
int onLight = 8; //Pin used to turn on button led
int motor = 10; //Pin used to control motor
int laser = 6; //Pin used to control laser
int mixer = 11; //Pin used to control mixer motor
int valve = 12; //Pin used to control valve
// New function to count the number of outliers
int darkPointsCounter = 0;
bool clockFlag = true; // Flag for turning the clock on/off
//Initiating analog pins
int LDR = A0; //Pin used to measure light dependant resistor (Analog)
//Variables for when the car is running
bool switchOn = false; //Create boolean to check if circuit is switched on or not
bool shutDown = false;//bool for status to shut down system
int optoVal ; //Create optoVal
int switchVal = 0;//Create default value for switch pin (input)
int count;
int countFIVE;
double distance;
int encoderRef;
double carSpeed;
//functions
void checkOnSwitch();
void startClock(double ldrVal);
bool clockAboveThreshold(int ldrRef);
//Assigning pins inputs/outputs
void setup(){
pinMode(encoderSensor,INPUT);
pinMode(startButton,INPUT); //set start in pin to input
pinMode(onLight,OUTPUT);
pinMode(motor,OUTPUT); //set motor pin to output
digitalWrite(motor,LOW); //set motor
pinMode(laser,OUTPUT); //set start out pin to output
digitalWrite(laser,HIGH);//keep laser on
pinMode(mixer,OUTPUT); //set mixer pin to output
digitalWrite(mixer,LOW); //set mixer pin to off
pinMode(valve, OUTPUT);
Serial.begin(9600);//begin communication with serial monitor
}
// Void loop
void loop (){
int ldrVal = analogRead(LDR);//Prevent car from starting until ref value is read
///////////////////////////////////////////////
// This block is for flashing LEDs
///////////////////////////////////////////////
while(ldrVal < ldrRefl || ldrVal > ldrRefu){ //Blink light every 100 ms to indicate to user that value is not at reference
digitalWrite(onLight,HIGH);
delay(100);
digitalWrite(onLight,LOW);
delay(100);
ldrVal = analogRead(LDR); //read ldr value
//Serial.println(ldrVal);
if (digitalRead(startButton) != 0){//hold button for 10 seconds to reset LED REF value
digitalWrite(onLight,HIGH);
long resetTimeRef = millis(); //begin countdown to reset
while(startButton != 0){
long timeElapsed = millis() - resetTimeRef;
if (timeElapsed > 10000){
ldrRef = analogRead(LDR); //reset ref value
digitalWrite(onLight,LOW);
}
}
}
}
delay(300);
Serial.println("LDR at reference. \n");
///////////////////////////////////////////////
// Car check on/off switch here
///////////////////////////////////////////////
// This function keeps looping until we turn the switch on.
checkOnSwitch();
// Initialize encoder and time counter variables
shutDown = false;
count = 0;
countFIVE = 0;
distance = 0;
darkPointsCounter = 0;
// Check initial encoder wheel position
int encoderRef = digitalRead(encoderSensor);
delay(50);
// Start the total time timer before the 5 second delay
long totalTimeInit = millis();
long totalTime;
// Start checking clock
// open valve, and mixer; wait 5 seconds for fluid to pass into reactor,
// then begin the motor.
digitalWrite(valve, HIGH);
analogWrite(mixer, MIXERSPEED);
//delay(5000);
//digitalWrite(valve,LOW);
digitalWrite(motor,HIGH);
///////////////////////////////////////////////
// INITIALIZE APP TIMER VARIABLES
///////////////////////////////////////////////
// Start the car runtime timer after the 5 second delay
long carTimeInit = millis();
long carTime;
bool encoderFlag;
// While LDR value is above threshold
while (clockAboveThreshold(ldrRef) && digitalRead(startButton) == 0){
carTime = millis() - carTimeInit; // Count car time elapsed in millisecs
// Report values every 5 seconds
if (carTime % REPORTTIME == 0){
distance = (double) countFIVE*1.0/(double)ENCODERRESOLUTION*(double)(WHEELDIAMETER)*3.14;
carSpeed = (double) distance*1.0/5.0;
Serial.print("five count: ");
Serial.print(countFIVE);
Serial.print("LDR:");
Serial.println(analogRead(LDR));
Serial.print("Time (s): ");
Serial.println(carTime);
Serial.print("Distance (cm): ");
Serial.println(distance);
Serial.print("Velocity (cm/s): ");
Serial.println(carSpeed);
countFIVE = 0;
}
// Check if encoder position has changed
// Reference is the initial encoder value (either dark or light, or 1 or 0)
if(digitalRead(encoderSensor) != encoderRef){
count++;
countFIVE++;
encoderRef = digitalRead(encoderSensor);
}
//Serial.println(count);
//Serial.println(digitalRead(encoderSensor));
}
///////////////////////////////////////////////////////
// Once the clock is triggered, or button pressed
// Report final values and turn of motor and mixer
///////////////////////////////////////////////////////
// Calculate total time (which is before the 5 second delay for the motor)
totalTime = millis() - totalTimeInit;
// Turn off the motor and valve
digitalWrite(motor, LOW);
analogWrite(mixer, 0);
digitalWrite(onLight,LOW);
digitalWrite(valve,LOW);
// Calculate the distance
distance = (double) count*1.0/(double)(ENCODERRESOLUTION)*WHEELDIAMETER*3.14;
// Print out 2 timers, before and after delay
Serial.println("LDR Value: ");
Serial.println(analogRead(LDR));
Serial.println("Distance: ");
Serial.println(distance);
Serial.println("Car time: ");
Serial.println(carTime);
Serial.println("Total time: ");
Serial.println(totalTime);
switchOn = false;
delay(2000);
}
// This function checks the start button.
// It stays in loop while the user holds down the
// button and only progresses once the user lets go of the button
void checkOnSwitch(){
while(!switchOn){ // While switch is off (false)
delay(100);//wait 100 ms
if (digitalRead(startButton)==BUTTONPRESSED){//if button is pressed activate switch
switchOn=true;
digitalWrite(onLight, HIGH);
while(digitalRead(startButton)==BUTTONPRESSED){}//keep car from running until pin reads 0 again
}
}
Serial.println("The car is on. \n");
}
// Check clock if below ref value shut off car
bool clockAboveThreshold(int ldrRef){
// This function would return true by default if the clock is not triggered
clockFlag = true;
// If the LDR value is below the threshold
// Increment a counter, counting the amount of points below the threshold
if (analogRead (LDR) < (ldrRef-DLDR)){
darkPointsCounter = darkPointsCounter + 1;
}
// If the number of points below the threshold is above 100 (for example)
// Set clock to triggered and return this value
if(darkPointsCounter > DARKPOINTSTHRESHOLD){
clockFlag = false;
}
return clockFlag;
}
$$H_2O_2 + 2I^- + 2H^+ \rightarrow I_2 + 2H_2O$$
$$2S_2O_3^{2-} + I_2 + 2H^+ \rightarrow S_4O_6^{2-} + 2I^-$$