I have a little problem dealing with ultrasonic sensor I want a simple thing , when the sensor read High pulse then after it low pulse , turns on the led so I try to make it with a 5cm distance and a flag , but it's dose not work help me please!

    #define echoPin 5
    #define trigPin 7
    int GREEN = 2;
    int YELLOW = 3;
    int RED = 4;
    int pos = 0;
    int flag = 0 ;
    long duration;
    int distance;
    void setup() {

  // put your setup code here, to run once:
    pinMode(GREEN, OUTPUT);
    pinMode(YELLOW, OUTPUT);
    pinMode(RED, OUTPUT);
    pinMode(trigPin, OUTPUT); // Sets the trigPin as an OUTPUT
    pinMode(echoPin, INPUT); // Sets the echoPin as an INPUT
    void loop() {
    if ( distance <= 5 && flag == 0)
      flag = 1 ;}
    } //high pulse (When the distance <=5)
    if ( distance >5 && flag == 1)
      red_light(); }
    }//the led should turned on when low pulse appears (When the distance >5)  
    void red_light()
    { digitalWrite(GREEN, LOW);
    digitalWrite(YELLOW, LOW);
    digitalWrite(RED, HIGH); }
    void ultra()
    { digitalWrite(trigPin, LOW);
    digitalWrite(trigPin, HIGH);
    digitalWrite(trigPin, LOW);
    duration = pulseIn(echoPin, HIGH);
    distance = duration*0.034/2; }

//this is my code
  • I don't quite understand, what you are trying to do here. So the red LED should light up, when the distance gets lower than 5cm. But what should then happen? Should it stay on forever? Should it go off, when the distance gets higher than 5cm? – chrisl Sep 23 at 11:43
  • no , the red led should light up when( distance gets lower than 5cm and then after that gets greater than 5cm ) , I try to turned in the led after I get ( a HIGH signal then LOW) – Majd Ramadan Sep 23 at 11:51
  • and yes I want it turned on forever . can u understand me now ? – Majd Ramadan Sep 23 at 11:52
  • 1
    what actually happens with this code is when I put something near the sensor <= 5 , the led is on without i removed the thing , but i want the led on ehen i put then removr the thing , how i should do this ? – Majd Ramadan Sep 23 at 12:31
  • 1
    @goodarduinocode it's a syntax error, but it's not the problem hear – Majd Ramadan Sep 23 at 12:33

what actually happens with this code is when I put something near the sensor <= 5 , the led is on without i removed the thing , but I want the led on when I put then remove the thing

Here is my theory on what happens here. You can confirm it by using one of the solutions, that I will explain below.

Currently your code is measuring the distance as fast as it can. The measurement is what takes the longest time in one iteration of the loop() function. Thus you get many many measurements per second. But such distance measurements are always noisy, meaning that the values change randomly in a specific range. When you put the object in front of the sensor, you expect the values to just go down, but actually they are sometimes rising again for 1 or 2 values because of the noise. So the measured values might look something like this (only imagined for making the point; not real values):

5.4 --> 5.2 --> 4.99 --> 5.001 --> 4.89 --> 4.90 --> 4.5

Overall the values go down, but you are comparing always the current value with the fixed threshold of 5cm. When the noise just raises the value again, while you pass 5cm, you will get a false "put and removed again" outcome. At the probability of the noise doing that is really high, since you measure that often and ultrasonic sensors are not accurate down to millimeters. You could even have the distance pass 5cm multiple times due to the noise.

There are some possibilities to reduce noise or to handle it.

  • Hysteresis: The first, that I would implement here is hysteresis. That means, that you set the "put" distance different than the "remove" distance. For example you could use 5cm as the distance to register, that the object is put in front of the sensor, but then you wait for the distance to go above 7cm to actually treat the object as "removed". You need to choose the difference between the distances larger than the noise (you can find that out via experimenting). This principle is also used directly with noisy digital signals on the Arduinos input pins. An Arduino Uno will treat voltages above about 2.6V as digital 1 (HIGH signal), and a value below 2.1V as digital 0 (LOW signal) (taken from the datasheet of the Atmega328P, which is the microcontroller on an Arduino Uno, while assuming the controller running on 5V like in an Arduino Uno). In electrical terms this is called a Schmitt-Trigger.

    For implementing this, you can just change the threshold values in your if statements.

  • You can reduce the noise by always measuring multiple times in a row and then calculating the mean value from it. Since a part of the noise is random, you can smoothe out this part a bit through taking the mean. That also reduces your time resolution, but in such a simple use case that mostly doesn't matter that much.

  • If the reaction time doesn't matter that much, you could reduce the frequency of measurements, so that subsequent distance measurements are already to far away from each other for the noise to create false triggers. This is worse than the other solutions, since it also depends on how fast you put the object in front of the sensor, but it is really easy to implement (just a simple delay() call, or better using millis() like in the BlinkWithoutDelay example for non-blocking code)

I would first implement the hysteresis. Then, if the difference in distances, that you need for it to work good, is too big for you, you can take the mean of multiple value to reduce the noise.

And just for protocol, as it already was said in the comments: Your first if statement has an extra closing bracket } which should not be there.

| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.