Sensors aren´t stoping car from moving

Hi! I’m working on a project for my robotics class, and I can’t figure out what I’m missing. I’ve watched a lot of videos trying to make it work, but I’ve reached a point where I don’t know what else to do.

The project involves building a car that can move in all directions, controlled by an app on my phone via Bluetooth. The car should also stop automatically when one of its two sensors detects an object too close. However, it should still be able to move in other directions. For example, if the front sensor detects an object at 10 cm, the car shouldn’t move forward but should still be able to move sideways or backward.

The car's base is made with 3D printing, 1 Arduino Uno, 1 expansion board for the Arduino Uno, 1 L298N Motor Drive Controller Board (DC Dual H-Bridge Robot Stepper), 2 DC motors, 2 rear wheels controlled by the motors, 1 "caster" wheel at the front that moves in all directions, 2 HC-SR04 proximity sensors, and 1 HC-05 Bluetooth module. Everything is powered by 6 AA batteries.

Here are the two codes I tested. The car moves fine, and the sensors are sending information, so they’re working. However, when they detect a distance of 10 cm or closer, the car doesn’t stop:

#include <SoftwareSerial.h>

// Bluetooth
SoftwareSerial bluetooth(10, 11); // RX on pin 10, TX on pin 11

// Motor A (left) pins
int IN1 = 2;
int IN2 = 4;
int speedA = 3;

// Motor B (right) pins
int IN3 = 6;
int IN4 = 7;
int speedB = 5;

// Sensor pins
#define TRIG_FRONT 12 // TRIG for the front sensor
#define ECHO_FRONT 13 // ECHO for the front sensor
#define TRIG_BACK 9   // TRIG for the back sensor
#define ECHO_BACK 8   // ECHO for the back sensor

// Speed variables
int leftSpeed = 200;        // Base speed for the left wheel
int rightSpeed = 226;       // Base speed for the right wheel
float reductionFactor = 0.2;
float diagonalReduction = 0.4; // Reduction factor for diagonals

// Car state
bool carOn = false;          // Initial state is off

void setup() {
  pinMode(IN1, OUTPUT);
  pinMode(IN2, OUTPUT);
  pinMode(IN3, OUTPUT);
  pinMode(IN4, OUTPUT);
  pinMode(speedA, OUTPUT);
  pinMode(speedB, OUTPUT);

  pinMode(TRIG_FRONT, OUTPUT);
  pinMode(ECHO_FRONT, INPUT);
  pinMode(TRIG_BACK, OUTPUT);
  pinMode(ECHO_BACK, INPUT);

  Serial.begin(9600);
  bluetooth.begin(9600);
  Serial.println("Bluetooth HC-05 ready. Send 'on' to turn on the car.");
}

void loop() {
  int frontDistance = measureDistance(TRIG_FRONT, ECHO_FRONT);
  int backDistance = measureDistance(TRIG_BACK, ECHO_BACK);
  // Print results to the serial monitor
  Serial.print("Front distance: ");
  Serial.print(frontDistance);
  Serial.println(" cm");

  Serial.print("Back distance: ");
  Serial.print(backDistance);
  Serial.println(" cm");

  Serial.println("------------------------");
  delay(500);

  if (bluetooth.available()) {
    String command = "";
    while (bluetooth.available()) {
      char character = bluetooth.read();
      command += character;
    }
    command.trim();
    processCommand(command);
  }
}

long measureDistance(int trigPin, int echoPin) {
  long duration;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);
  return duration * 0.034 / 2; // Distance in cm
}

void processCommand(String command) {
  long frontDistance = measureDistance(TRIG_FRONT, ECHO_FRONT);
  long backDistance = measureDistance(TRIG_BACK, ECHO_BACK);

  if (command == "on") {
    carOn = true;
    Serial.println("Car turned on.");
  } else if (command == "off") {
    carOn = false;
    stopMotors();
    Serial.println("Car turned off.");
  } else if (carOn) {
    if (command == "f" && frontDistance > 10) moveForward();
    else if (command == "a" && backDistance > 10) moveBackward();
    else if (command == "e") moveLeft();
    else if (command == "d") moveRight();
    else if (command == "s") stopMotors();
    else if (frontDistance <= 10) stopMotors();
    else if (backDistance <= 10) stopMotors();
    else Serial.println("Command not recognized.");
  } else {
    Serial.println("Car is off. Send 'on' to turn it on.");
  }
}

void moveForward() {
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void moveBackward() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, HIGH);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, HIGH);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void moveLeft() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, HIGH);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void moveRight() {
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, HIGH);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void stopMotors() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, 0);
  analogWrite(speedB, 0);
}

#include <SoftwareSerial.h>

// Bluetooth
SoftwareSerial bluetooth(10, 11); // RX on pin 10, TX on pin 11

// Pins for motor A (left)
int IN1 = 2;
int IN2 = 4;
int speedA = 3;

// Pins for motor B (right)
int IN3 = 6;
int IN4 = 7;
int speedB = 5;

// Ultrasonic sensor pins
#define TRIG_FRONT 12  // TRIG pin for the front sensor
#define ECHO_FRONT 13  // ECHO pin for the front sensor
#define TRIG_BACK 9    // TRIG pin for the back sensor
#define ECHO_BACK 8    // ECHO pin for the back sensor

// Speed variables
int leftSpeed = 200;
int rightSpeed = 226;
float reductionFactor = 0.2;
float reductionFactor2 = 0.4;

// Car state
bool carOn = false;

// Sensor-detected distances
int frontDistance = 0;
int backDistance = 0;

// Distance limit
int distanceLimit = 10; // Minimum distance to stop motors

void setup() {
  pinMode(IN1, OUTPUT);
  pinMode(IN2, OUTPUT);
  pinMode(IN3, OUTPUT);
  pinMode(IN4, OUTPUT);
  pinMode(speedA, OUTPUT);
  pinMode(speedB, OUTPUT);

  pinMode(TRIG_FRONT, OUTPUT);
  pinMode(ECHO_FRONT, INPUT);
  pinMode(TRIG_BACK, OUTPUT);
  pinMode(ECHO_BACK, INPUT);

  Serial.begin(9600);
  bluetooth.begin(9600);
  Serial.println("Bluetooth HC-05 ready. Send 'on' to turn the car on.");
}

void loop() {
  // Check distances before any command
  frontDistance = measureDistance(TRIG_FRONT, ECHO_FRONT);
  backDistance = measureDistance(TRIG_BACK, ECHO_BACK);

  // Display distances in the serial monitor
  Serial.print("Front distance: ");
  Serial.print(frontDistance);
  Serial.println(" cm");

  Serial.print("Back distance: ");
  Serial.print(backDistance);
  Serial.println(" cm");
  Serial.println("------------------------");

  // Read Bluetooth commands
  if (bluetooth.available()) {
    String command = "";
    while (bluetooth.available()) {
      char c = bluetooth.read();
      command += c;
    }
    command.trim();
    processCommand(command);
  }

  delay(100); // To avoid fast readings
}

void processCommand(String command) {
  if (command == "on") {
    carOn = true;
    Serial.println("Car turned on.");
  } else if (command == "off") {
    carOn = false;
    stopMotors();
    Serial.println("Car turned off.");
  } else if (carOn) {
    if (frontDistance < distanceLimit && command == "f") {
      Serial.println("Obstacle detected ahead. Movement not allowed.");
    } else if (backDistance < distanceLimit && command == "a") {
      Serial.println("Obstacle detected behind. Movement not allowed.");
    } else {
      executeCommand(command);
    }
  } else {
    Serial.println("Car is off. Send 'on' to turn it on.");
  }
}

void executeCommand(String command) {
  if (command == "f") forward();
  else if (command == "a") backward();
  else if (command == "e") left();
  else if (command == "d") right();
  else if (command == "s") stopMotors();
  else Serial.println("Command not recognized.");
}

int measureDistance(int trigPin, int echoPin) {
  long duration;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);
  return duration * 0.034 / 2; // Distance in cm
}

void forward() {
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void backward() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, HIGH);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, HIGH);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void left() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, HIGH);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void right() {
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, HIGH);
  analogWrite(speedA, leftSpeed);
  analogWrite(speedB, rightSpeed);
}

void stopMotors() {
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, LOW);
  analogWrite(speedA, 0);
  analogWrite(speedB, 0);
}

I also noticed that when using more than one proximity sensor, there are libraries available that allow all sensors to work simultaneously. Perhaps I'm missing something related to that.

Any help would be greatly appreciated. Thank you!

How many different variables named frontDistance do you have in your sketch ?

In these code lines

        else if (frontDistance <= 10)
            stopMotors();

which of the frontDistance variables is being tested ?

I belive that I only have this one:

void loop() {
  int frontDistance = measureDistance(TRIG_FRONT, ECHO_FRONT);

It measures the distance of the sensor, but I see that in

void processCommand(String command) {
  long frontDistance = measureDistance(TRIG_FRONT, ECHO_FRONT);
  long backDistance = measureDistance(TRIG_BACK, ECHO_BACK);

I have the variable again, maybe that is the problem?

I am not sure if it is causing whatever problem you have, but I would certainly eliminate the duplication of variable names

The scope of the variables should prevent any confusion but better safe than sorry

When I took it out I had this error:

Please do not post pictures of code and/or errors. Copy them from the IDE and post them here in code tags

As to the errors, before you can use a variable in a function it either has to be declared locally in that function or to be declared globally outside of any function. The code that you posted does neither of these, hence the error

Go back to your original code and change name of the duplicate variables in one of the functions

Hi, @crogued
Welcome to the forum.

You only need to read most of your inputs once in your code.
At the start of the loop, then use the assign variables in the rest of the code and act on it, then back to the top your code you read your inputs again.

What you are doing is taking a snapshot of your project on each loop of the code.

Tom... :grinning: :+1: :coffee: :australia:

Hi guys, I got it, after all I just need to include this in the void loop so it constantly verifies if the distance is good to keep the motors on or off:

// Distance-based motor control
  if (frontDistance <= 30 || backDistance <= 30) {
    digitalWrite(IN1, LOW);
    digitalWrite(IN2, LOW);
    digitalWrite(IN3, LOW);
    digitalWrite(IN4, LOW);
    analogWrite(speedA , 0);
    analogWrite(speedB , 0);
    delay(100);
  }

Thank you so much!

Please post the full working sketch

How will this let the car move backward if frontDistance <= 30 and vice versa?

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.