clap on/off light not working w/ vibration sensor

I am trying to create a program that uses the piezo vibration sensor to turn a light on/off. this is a wall light so I am using a servo to flip the switch. When I clap I want to turn the light on and wait for another clap. then I want it to turn the light off. The vibration sensor works and when it goes above the threshold it triggers the servo, in the first if statement. However it seems as soon as that happens it takes that same reading and applies it to the second if statement, so I will always have the servo move back when I clap once. I tried fiddling with the timing so it would go below the threshold before it sets go = 2, but it won’t work. Any ideas?

#include <Servo.h>
int GroundPin= 0;
int sensePin = 1;
int go = 1;
Servo light;

int threshold= 1000;

void setup()
{
Serial.begin(9600);
pinMode(GroundPin, OUTPUT);
digitalWrite(GroundPin, LOW);
light.attach(9);
}

void loop()
{
int reading = analogRead(sensePin);
Serial.println(sensePin);
if((reading > threshold) && (go == 1))
{
light.write(180);
delay(2000);
go = 2;
}
Serial.println(sensePin);
if((reading > threshold) && (go == 2))
{
light.write(0);
delay(2000);
go = 1;
delay(2000);
}
delay(2000);
}

With 12 posts, you should know better. Go back and read Nick Gammon's post at the top of this Forum on the proper way to post source code using code tags. You'll likely get more responses if you do.

Edit: You can edit your post

When you reach your second if statement, reading still has a value above threshold. Add a line 'reading = 0;' after you turn the servo.

Also, remove the delay at the end of your main loop. You'll never sense the clap with that in there. I believe you put it in so you could read your debug prints, but that will break the script.

Pat.

that works Gabriel_swe! thanks. I was thinking along that route but didn't know exactly what to do. next time I will use code tags.

ok, it stopped working, could I have it wait until it reaches zero until it moves to the second if statement? also somehow that for() is giving me errors.

#include <Servo.h>
int GroundPin= 0;
int sensePin = 0;
int go = 2;
Servo light;


int threshold= 1000;


void setup()
{
 light.write(150);
Serial.begin(9600);
pinMode(GroundPin, OUTPUT);
digitalWrite(GroundPin, LOW);
light.attach(9);
}


void loop()
{

int reading = analogRead(sensePin);
delay(500);
Serial.println(reading);
if((reading > threshold) && (go == 1))
{   
  light.write(130);
  reading = 0;
  delay(500);
  go = 2; 
}
delay(500);
for(reading < threshold)
{
if((reading > threshold) && (go == 2))
{   
  light.write(160);
  reading = 0;
  delay(500);
  go = 1; 
  
}
}
}

That just doesn't sound very right.... See comments next to your pin definition, Especially 1st one. Second one is cosmetic

int GroundPin= 0; // you should think twice about using that pin and using serial...
int sensePin = 0; // use A0 for readability

Two errors:

  1. Remove the delays in your main loop, or you'll miss your clap. You'll ones to remove the prints also. (The delays IN the if's are ok.)

  2. Somewhere along the way you added a 'for' loop that is not right. Remove it and the closing bracket and you should be fine again.

so it was working for a bit, giving me numbers around 500. but then it went wacke and only gave me numbers close to 0 and 1023. I took the sensor off the breadboard, but it keep reading those number and moving the servo. what?

Did you read my comment above?

Don't use digital pin 0 It is used for serial communication when you do your prints (0 and 1023 are 0 and 1 going through that pin)

I have A0 hooked up to the negative on the sensor and A1 hooked up to the positive

WILL_STEF: so it was working for a bit, giving me numbers around 500. but then it went wacke and only gave me numbers close to 0 and 1023. I took the sensor off the breadboard, but it keep reading those number and moving the servo. what?

Did a search för piezo vibration sensor on ebay, and common is a rectangular version that can produce +/- 90 volt. If used as a sound sensor and a clap max out the analog input (5 volt, 1023 in digital value), I think the input is in danger if you accidently touch or hit the sensor if you don't have a protective circuit.

WILL_STEF: I have A0 hooked up to the negative on the sensor and A1 hooked up to the positive

Is A0 the one you call groundPin and that you set to ground by doing

Int GroundPin =0;

......


pinMode(GroundPin, OUTPUT);
digitalWrite(GroundPin, LOW);
l

?

I think so, I made this code some time ago and only got back to it recently.

  1. You may be connecting to A0 and A1, but your code is connecting BOTH wires to 0.

  2. Go back and look at my comments. You cannot have delays in the main loop if you hope to catch the signal!

  3. Lose the 'for' statement.

Pat

WILL_STEF: I think so, I made this code some time ago and only got back to it recently.

if you want to use A0 and A1, you should call them that. You can use digital functions with A0, A1 in which case Analog 0 to 5 are called digital pin 14 through digital pin 19.

but when you do

pinMode(GroundPin, OUTPUT);
digitalWrite(GroundPin, LOW);

you are addressing digital pin 0 - which is the RX of your Serial connection, so definitely an input.. You are making that an OUTPUT and the setting it to LOW.. that might lead to uncertain conditions.

pinMode(A0, OUTPUT);
digitalWrite(A0, LOW);

would be more adapted (well with #define GroundPin A0 you would be good to go)

The question is why do you do this though while there is a nice GND pin available right next to the Analog pins for you to use.