My Roaming robot has recently been giving me some problems, specifically regarding the power distribution between the 2 motors (with one wheel sporadicly turning faster than the other). I initially thought that one of the motors might have been damaged so I replaced both, only to have the problem remain. After some testing and replacing both the Pololu Dual MC33926 Motor Driver Shield and the Arduino Uno R3, I determined that the problem lay with the Pololu Motor shield. I am not sure if one of the other sensors or actuators was causing some interference on the shield or if it is simply a design flaw in the shield, but I found it impossible to balance the power of the 2 motors.
I thus decided to replace the Pololu Dual MC33926 Motor Driver Shield with a Pololu DRV8833 Dual Motor Driver Carrier, and this resolved the problem I was experiencing.
Here the Pololu Dual MC33926 Motor Driver Shield and the Pololu DRV8833 Dual Motor Driver Carrier can be seen side by side (the Pololu DRV8833 Dual Motor Driver Carrier being the much smaller of the 2):
I mounted the Motor driver on a bread board, attached on top of an Adafruit Proto-shield. This has the added benefit of having screw terminals for the Arduino pins, so that the jumper cables can no longer accidentally become dislodged.
To install the new DRV8833 Motor Driver I had to switch some of the pin usage on the Arduino in order to free up some PWM digital pins needed by the motor driver. The new Layout is as follows:
Analog Pins:
- A0
- A1
- A2 – Servo
- A3
- A4 – IR Sensor
- A5 – Photo-resistor
Digital Pins:
- 0
- 1
- 2 – LED
- 3 – Motor Driver B IN 1
- 4
- 5 – Motor Driver B IN 2
- 6 – Motor Driver A IN 1
- 7 – Ultrasonic Sensor
- 8 – Right Trigger Switch
- 9 – Motor Driver A IN 2
- 10
- 11 – Left Trigger Switch
- 12
- 13
Here are the updated drawings illustrating the wiring of the different components:
I also replaced some of the wiring to the Ultrasonic sensor as they had become worn due to the “neck movement” of the servo pointing the sensor in different directions.
I also ran the power for the Ultrasonic sensor straight from the Arduino and no longer via the Proto-board, this was simply to give the cables a bit more play for the “neck movement” performed by the servo.
After these changes the little guy is working perfectly again.
I will be posting a video of this robot in action in the near future.
Here is the updated code for the robot:
#include "Servo.h" #define IR_PIN A4 #define SERVO_PIN A2 #define PING_PIN 7 #define BUMPER_LEFT_PIN 11 #define BUMPER_RIGHT_PIN 8 #define LDR_PIN A5 #define LED_PIN 2 #define IR_DROP 500 //Distance considered a potential drop #define MIN_LIGHT 300 //Level of light to turn on LED for light #define BIN_1 3 #define BIN_2 5 #define AIN_1 6 #define AIN_2 9 #define MAX_PWM_VOLTAGE 150 int IRDist = 0; int bpLeft = 0; int bpRight = 0; int LDRValue = 0; const int dangerThresh = 16;// (in cm) used for obstacle avoidance int leftDistance, rightDistance; //distances on either side Servo panMotor; //'neck' servo long duration; //time it takes to recieve PING signal void setup() { Serial.begin(9600); //used for serial communication for debugging pinMode(BUMPER_LEFT_PIN,INPUT); pinMode(BUMPER_RIGHT_PIN,INPUT); pinMode(LED_PIN, OUTPUT); pinMode(BIN_1, OUTPUT); pinMode(BIN_2, OUTPUT); pinMode(AIN_1, OUTPUT); pinMode(AIN_2, OUTPUT); } void moveStop() { digitalWrite(BIN_1, LOW); digitalWrite(BIN_2, LOW); digitalWrite(AIN_1, LOW); digitalWrite(AIN_2, LOW); } void moveForward() { digitalWrite(BIN_1, LOW); analogWrite(BIN_2, MAX_PWM_VOLTAGE); analogWrite(AIN_1, MAX_PWM_VOLTAGE); digitalWrite(AIN_2, LOW); delay(300); } void turnLeft() { digitalWrite(BIN_1, LOW); analogWrite(BIN_2, MAX_PWM_VOLTAGE); digitalWrite(AIN_1, LOW); analogWrite(AIN_2, MAX_PWM_VOLTAGE); delay(300); } void turnRight() { analogWrite(BIN_1, MAX_PWM_VOLTAGE); digitalWrite(BIN_2, LOW); analogWrite(AIN_1, MAX_PWM_VOLTAGE); digitalWrite(AIN_2, LOW); delay(300); } void moveBack() { analogWrite(BIN_1, MAX_PWM_VOLTAGE); digitalWrite(BIN_2, LOW); digitalWrite(AIN_1, LOW); analogWrite(AIN_2, MAX_PWM_VOLTAGE); delay(500); } int checkDrop() { pinMode(IR_PIN,INPUT); IRDist = analogRead(IR_PIN); //Serial.println(IRDist); if(IRDist < IR_DROP) { return 1; //Drop present (determined with IR distance sensor) } else { return 0; } } void lightDarkness() { LDRValue = analogRead(LDR_PIN); if(LDRValue < MIN_LIGHT) { digitalWrite(LED_PIN,HIGH); //It is dark, turn on the light } else { digitalWrite(LED_PIN,LOW); } } int checkLeftBumper() { bpLeft = digitalRead(BUMPER_LEFT_PIN); if(bpLeft == HIGH) { //Serial.println("Left Bumper"); //HIT! return 1; } else { return 0; } } int checkRightBumper() { bpRight = digitalRead(BUMPER_RIGHT_PIN); if(bpRight == HIGH) { //Serial.println("Right Bumper"); //HIT! return 1; } else { return 0; } } void compareDistance() { if (leftDistance>rightDistance) //if left is less obstructed { turnLeft(); } else if (rightDistance>leftDistance) //if right is less obstructed { turnRight(); } else //if they are equally obstructed { moveBack(); } } long ping() { // Send Ping pulse pinMode(PING_PIN, OUTPUT); digitalWrite(PING_PIN, LOW); delayMicroseconds(2); digitalWrite(PING_PIN, HIGH); delayMicroseconds(5); digitalWrite(PING_PIN, LOW); //Get duration it takes to receive echo of Ping sent pinMode(PING_PIN, INPUT); duration = pulseIn(PING_PIN, HIGH); //Convert duration into distance (cm) return duration / 29 / 2; } void loop() { lightDarkness(); if(checkDrop() == 1) { moveBack(); moveBack(); moveBack(); turnRight(); } else if(checkLeftBumper() == 1) { moveBack(); turnRight(); } else if(checkRightBumper() == 1) { moveBack(); turnLeft(); } else { moveStop(); int distanceFwd = ping(); //Serial.println(distanceFwd); if (distanceFwd>dangerThresh) //if path is clear { moveForward(); } else //if path is blocked { moveStop(); panMotor.attach(SERVO_PIN); panMotor.write(20); //look right delay(400); rightDistance = ping(); //scan to the right panMotor.write(160); //look left delay(550); leftDistance = ping(); //scan to the left panMotor.write(90); //look to center delay(400); panMotor.detach(); compareDistance(); } } }
that is so cool 🙂
LikeLiked by 1 person