Loading...
  Show Posts
Pages: [1]
1  Using Arduino / Motors, Mechanics, and Power / Re: Looking for help getting DC motor to brake with L293D chip on: October 03, 2012, 04:42:49 pm
Thanks DC42, I also just today found the below, so it looks like the next step is a Mosfet H-bridge !

http://arduino.cc/playground/Main/AdafruitMotorShield

// The L293D motor driver ic doesn't have a good
// brake anyway.
// It uses transistors inside, and not mosfets.
// Some use a software break, by using a short
// reverse voltage.
// This brake will try to brake, by enabling
// the output and by pulling both outputs to ground.
// But it isn't a good break.
2  Using Arduino / Motors, Mechanics, and Power / Looking for help getting DC motor to brake with L293D chip on: October 02, 2012, 04:24:40 pm
Hello, I am experimenting with the L293D chip to power a small DC motor.
I have the chip hooked up so that both sides power my one motor, hopefully resulting in a little higher output amp potential as compared to powering the motor with just one side of the chips pins (?).
My simple program is working fine, except there is no braking force being applied when both direction pins are either both LOW, or both HI. Am I doing something wrong in the code, is the L293D hooked up incorrectly, or is it something with the particular motor that I am using?
I have tried the motor brake with the same code just using one side of the chip, with the same results.
I have tried two different motors with the same results. I can measure that both direction pins are going HIGH during the brake command (4.9v), but there is no braking resistance in the motor.
I have the L293D enable pins permanently wire to HIGH, and there is a description of the rest of the pin hook ups at the top of my code.
Any advice, help, suggestions are appreciated!

Code:
/* DC motor speed and direction using L293DNE IC (Texas Instm) 10-3-2012
L293DNE pinouts, set up for one motor being driven by both sets of H-bridges
  Pin 1, 9, 16 to +5V
  Pin 2 & 15 to Arduino PWM pin 5
  Pin 3 & 14 to motor lead A
  Pin 4, 5, 12 , 13 to Grnd
  Pin 6 & 11 to motor lead B
  Pin 7 & 10 to Arduino PWM pin 6
  Pin 8 to +V battery, battery negative to common Grnd
*/
int motorPin1 = 5;    // direction pin to Driver board Pin "D1", pins 7 & 10 on L293D chip
int motorPin2 = 6;   // direction pin to Driver board Pin "D2", pins 2 & 15 on L293D chip
//
void setup () {
  pinMode(motorPin1,OUTPUT);        //set pin 3 as output, L293D direction 1
  pinMode(motorPin2,OUTPUT);        // set pin 4 as output, L293D direction 2
}
//
void loop() {
    motorSpin();
 }
//
int motorSpin(){
  analogWrite(motorPin1,255); // PWM the direction pin (L293D pin 2)
  digitalWrite(motorPin2,LOW);
  delay(1000);
   
  digitalWrite(motorPin1,HIGH); // should be brake
  digitalWrite(motorPin2,HIGH);
  delay(2000);
 
  digitalWrite(motorPin1,LOW); // motor goes the other direction
  analogWrite(motorPin2,255);   // PWM the other direction pin (L293D pin 7)
  delay(1000);
 
  digitalWrite(motorPin1,HIGH); // another brake
  digitalWrite(motorPin2,HIGH);
  delay(2000);
  }
3  Using Arduino / Programming Questions / Re: Looking for assistance with summing encoder counts on: August 18, 2012, 10:13:31 pm
wonderful, I knew there was a cleaner way to do it!
thanks again for the help
4  Using Arduino / Programming Questions / Looking for assistance with summing encoder counts on: August 17, 2012, 12:46:38 pm
Hello, I have been going in circles ( no pun intended) for two days with this and I am not getting anywhere.
I have a simple DC motor and encoder from here: http://www.pololu.com/catalog/product/1447
I am using 3 pushbuttons to send the motor to 3 different positions – which are + 1 rev, + 2 rev and then reverse one rev.
I am counting encoder pulses in the serial monitor and I am trying to sum the all of the encoder moves to see how far off I am from my desired tick count. The motor overshoots the desired tick count, which is fine for now. My plan is to then to try and implement PID control to see if I can hit my encoder counts to the same number as the desired tick number.
My problem now is I can’t get the math right for summing encoder counts after each push button. I have a two second pause in the print command to let the motor reach its position before I print the counts to the monitor. As I understanding it the counts stay in memory until a new “move” command is run and then the count zeros and starts counting again until the motor stops.
So I push button 1, get a count, but then I am trying to zero the counter, push button 1 (or 2 or 3)  then add the new count to the old count and get a total count.  Simply put, I want to push any combination of forward and reverse buttons (pausing in-between to let the motor reach its destination) for 20 repetitions and be able to see how many counts I am off from my desired tick count.
I have tried zeroing the count in between button pushes, using the button to trigger a math function to add to the count (doesn’t work as it takes 1-2 seconds for the motor to reach its final count), looking at a change in counts using a compare function (works when the count is different but not when the same button is pushed over and over), and a couple of other methods.
I always get a constant summing of counts even when there are no button pushes, or I can’t get the count to increment at all.
Here is my non-working code, for now I have commented out push buttons 2 and 3.

I feel I am going about this incorrectly and I should take an entirely new approach - any guidance or suggestions are welcome, thank you


Code:
// MD03A_Motor_basic + encoder
//credit to: KAS http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1282384853
// credit to JohnWasser
//
const int InA1       = 10;      // Pin 10, goes to Pololu INA motor direction pin (low forward, high reverse)
const int InB1       = 11;      // Pin 11, goes to Pololu INB motor direction pin (low reverse, high forward)
const int PWM1    =    6;       // Pin 6, goes to Pololu PWM pin (speed)
const int encodPinA1 =  3;       // Pin 3, reads encoder A signal (yellow)
//const int encodPinB1  = 8;       // Pin 8, reads encoder B signal (White)
const int FORWARD   =  1;       //
const int BACKWARD  =  2;      //
const int buttonPin =  A0;      // Analog pin A0, reads Voltage of button 1, 2, or 3
unsigned long lastMilli = 0;       // loop timing
unsigned long lastMilliPrint = 0;  // loop timing
volatile long count = 0;              // motion counter
volatile long ticks = 0;              // motion end point
volatile boolean run = false;         // motor moves
int buttonValue = 0;       // defines switchValue as an interger, sets value at 0 (of 0 -1023)

long previousMillis = 0;        // will store last time print was updated
long interval = 200;           // interval at which to print

int lastCount = 0;
int totalCount = 0;
int lastMove = 0;
int oldCount = 0;

//

void setup() {
  pinMode(InA1, OUTPUT);           // direction to Pololu motor board
  pinMode(InB1, OUTPUT);           // direction to Pololu motor board
  pinMode(PWM1, OUTPUT);           // PWM output to Pololu motor board
  pinMode(encodPinA1, INPUT);      // input from encoder
  //pinMode(encodPinB1, INPUT);      // input from encoder
  pinMode(buttonPin,INPUT);           // pin A0, reads V input from buttons
  digitalWrite(encodPinA1, HIGH);      // turn on pullup resistor pin 10
  //digitalWrite(encodPinB1, HIGH);      // turn on pullup resistor pin 11
  attachInterrupt(1, rencoder, FALLING);
  Serial.begin(9600);                 // set up Serial library at 9600 bps
 
}

void loop()
          {
  buttonValue = analogRead(buttonPin);   // Read Voltage on pin A0
  {
  if(buttonValue>940)                   // Button #1 470 resistor 992 max (1023=5v)
    {
      moveMotor(FORWARD, 250, 2000*1);      // direction, PWM (speed), ticks number (2000=360°)
      addCount;                          // calls math function to add current count
    }
  }
   
  //buttonValue = analogRead(buttonPin); 
    //if(buttonValue>750 && buttonValue<800)  // Button #2 4.7k resistor  790 max, min = less than bttn #1
    //moveMotor(FORWARD, 250, 2000*2);        // direction, PWM (speed), ticks number (2000=360°)   
 
  //buttonValue = analogRead(buttonPin); 
  //if(buttonValue>600 && buttonValue<630)  // Button #3 10k resistor  620 max, min = less than bttn #2
    //moveMotor(BACKWARD, 250, 2000*1);       // direction, PWM (speed), ticks number (2000=360°)
   
     printCount(2000);   // prints count every  2 seconds
 }
 
void moveMotor(int direction, int PWM_val, long tick)  {
  count = 0;                                // abs(count)
  ticks = tick;
  if(direction==FORWARD)   
    motorForward(PWM_val);
  else
    if(direction==BACKWARD)   
    motorBackward(PWM_val);
}
void rencoder() {                           // pulse and direction, direct port reading to save cycles
  count++;
  if(run && count >= ticks)     
    motorBrake();
}

void motorForward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, LOW);
  digitalWrite(InB1, HIGH);
  run = true;
}

void motorBackward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, LOW);
  run = true;
}

void motorBrake()  {
  analogWrite(PWM1, 0);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, HIGH);
  run = false;
}

void addCount()
  {
    lastMove = count;
  }

void printCount(long interval) // function "blink", "interval" is a "long" parameter assigned to the "blink" function
                          // 1000 is passed into "interval" when "blink(1000)" is run
    {
     if (millis() - previousMillis > interval) // if (current time - below marked time > 1000) is true, then run below
        {
          previousMillis = millis();  // mark the time when the above is true (current time - previous time > 1000)
          totalCount = (lastMove + oldCount);
          oldCount = count;
          Serial.print("total  "  );
          Serial.println(totalCount);
         }
    } 
5  Using Arduino / Programming Questions / Re: delay program, looking for understanding of how it works on: August 15, 2012, 04:12:53 pm
ahh, got it, it is slowly sinking in (I hope), thank you!
6  Using Arduino / Programming Questions / delay program, looking for understanding of how it works on: August 15, 2012, 10:41:28 am
Hello, this program is from the “Arduino Cookbook” .
The program works fine, however I am trying to understand the purpose of the “duration” and “interval” parts of the code.
 Are these merely character placeholders that allow the
“ while (millis() - start <= duration” and the “if (millis() - previousMillis > interval)” statements to always result to be true?
Since “duration” and “interval” aren’t declared or assigned I can change this text to anything and the code still works.
I guess my confusion comes from the fact that “duration” and “interval” are not declared in setup, so how can they be successfully be used in a mathematical equation?

The explanation of these two lines of code is probably obvious to experienced users, any explanation of the function of this code to a non-CC++ and Arduino newbie is much appreciated.

Code:
//blink an led for a set amount of time
// from Aurduino Cookbook
//
const int ledPin = 13;  // led is on pin 13
int ledState = LOW;     // set intial led pin state to low
long previousMillis = 0; // will store the last time the LED was updated

void setup()
  {
    pinMode(ledPin, OUTPUT);
    Serial.begin(9600);
  }

void loop()
  {
    Serial.println(millis() / 1000); // print elapsed time in seconds (milli/1000)
       mydelay(4000);                // run "mydelay" function every millisecond*4000 (four seconds)
  }
 
void mydelay(unsigned long duration)  //function "myDelay" sets "duration" as unsigned long, also runs "blink" function
  {
    unsigned long start = millis();      // assigns "start" to current time
    while (millis() - start <= duration) // while this is true then do the below (current time - start) always true?
    {
      blink(1000);       // run "blink" function every (xxx milliseconds)
    }
  }
void blink(long interval) // blink function
  {
   if (millis() - previousMillis > interval) // if this is true then run the below (always true ?)
     {
       previousMillis = millis();    // save the last time the LED blinked
       if (ledState == LOW)
          ledState = HIGH;
       else
           ledState = LOW;
       digitalWrite(ledPin, ledState);
     }
  }
7  Topics / Robotics / Re: DC motor / Encoder not responding correctly after reset on: August 14, 2012, 02:30:34 pm
Need helo again - I am trying to serial print the encoder count once every two seconds.
I commented out some of the loop functions so that I was just looking at one button push.
Can you take a look at my "printcount" function at the end of this code and suggest how I can print the encoder count every two seconds for just one line?
thank you



Code:
// MD03A_Motor_basic + encoder
//credit to: KAS http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1282384853
// credit to JohnWasser
//
const int InA1       = 10;      // Pin 10, goes to Pololu INA motor direction pin (low forward, high reverse)
const int InB1       = 11;      // Pin 11, goes to Pololu INB motor direction pin (low reverse, high forward)
const int PWM1    =    6;       // Pin 6, goes to Pololu PWM pin (speed)
const int encodPinA1 =  3;       // Pin 3, reads encoder A signal (yellow)
//const int encodPinB1  = 8;       // Pin 8, reads encoder B signal (White)
const int FORWARD   =  1;       //
const int BACKWARD  =  2;      //
const int buttonPin =  A0;      // Analog pin A0, reads Voltage of button 1, 2, or 3
unsigned long lastMilli = 0;       // loop timing
unsigned long lastMilliPrint = 0;  // loop timing
volatile long count = 0;              // motion counter
volatile long ticks = 0;              // motion end point
volatile boolean run = false;         // motor moves
int buttonValue = 0;       // defines switchValue as an interger, sets value at 0 (of 0 -1023)

long previousMillis = 0;        // will store last time LED was updated
long interval = 200;           // interval at which to print

long wait  =  2000;
long currentMillis = 0;
//

void setup() {
  pinMode(InA1, OUTPUT);           // direction to Pololu motor board
  pinMode(InB1, OUTPUT);           // direction to Pololu motor board
  pinMode(PWM1, OUTPUT);           // PWM output to Pololu motor board
  pinMode(encodPinA1, INPUT);      // input from encoder
  //pinMode(encodPinB1, INPUT);      // input from encoder
  pinMode(buttonPin,INPUT);           // pin A0, reads V input from buttons
  digitalWrite(encodPinA1, HIGH);      // turn on pullup resistor pin 10
  //digitalWrite(encodPinB1, HIGH);      // turn on pullup resistor pin 11
  attachInterrupt(1, rencoder, FALLING);
  Serial.begin(9600);                 // set up Serial library at 9600 bps
 
}

void loop()
          {
           
  buttonValue = analogRead(buttonPin);   // Read Voltage on pin A0
  if(buttonValue>940)                   // Button #1 470 resistor 992 max (1023=5v)
    moveMotor(FORWARD, 250, 2000*1);      // direction, PWM (speed), ticks number (2000=360°)
   
  printCount(); 
   
  //buttonValue = analogRead(buttonPin); 
    //if(buttonValue>750 && buttonValue<800)  // Button #2 4.7k resistor  790 max, min = less than bttn #1
    //moveMotor(FORWARD, 250, 2000*2);        // direction, PWM (speed), ticks number (2000=360°)   
 
  //buttonValue = analogRead(buttonPin); 
  //if(buttonValue>600 && buttonValue<630)  // Button #3 10k resistor  620 max, min = less than bttn #2
    //moveMotor(BACKWARD, 250, 2000*1);       // direction, PWM (speed), ticks number (2000=360°)
 
 }
 
void moveMotor(int direction, int PWM_val, long tick)  {
  count = 0;                                // abs(count)
  ticks = tick;
  if(direction==FORWARD)   
    motorForward(PWM_val);
  else
    if(direction==BACKWARD)   
    motorBackward(PWM_val);
}
void rencoder() {                           // pulse and direction, direct port reading to save cycles
  count++;
  if(run && count >= ticks)     
    motorBrake();
}

void motorForward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, LOW);
  digitalWrite(InB1, HIGH);
  run = true;
}

void motorBackward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, LOW);
  run = true;
}

void motorBrake()  {
  analogWrite(PWM1, 0);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, HIGH);
  run = false;
}

void printCount()  {
   currentMillis == millis();   
   if (currentMillis + wait <= millis())
    Serial.println(count);   
}
8  Topics / Robotics / Re: DC motor / Encoder not responding correctly after reset on: August 14, 2012, 12:31:47 pm
I decided to give it a try on my own, and made a nice mess of it, ran your code and it worked fine.
thank you!
9  Topics / Robotics / Re: DC motor / Encoder not responding correctly after reset on: August 10, 2012, 06:01:30 pm
ahh,  I was making this too complicated, I will give this code a try, thank you, I have a lot to learn!
10  Topics / Robotics / Re: DC motor / Encoder not responding correctly after reset on: August 08, 2012, 11:31:09 pm
thanks for the quick reply, I understand your point, but not sure that I can execute it in code!
11  Topics / Robotics / DC motor / Encoder not responding correctly after reset on: August 08, 2012, 05:37:11 pm
Hello, I am having puzzling operation my DC motor project that only happens during power up or after reset.
First, a thank you to “KAS” on the forum( @ http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1282384853) as I am using this code.

I am trying to control a DC motor to go to 3 discrete positions, using 3 buttons, as described below:
Push button 1: motor turns forwards 1 revolution
Push button 2: motor turns forwards 2 revolutions
Push button 3: motor turns backwards 1 revolution

This code is working wonderfully except right after reset – if I push button 3 first I get 1 rev backwards (which is correct), then if I push button 2 next I get 4 revs forwards, not my desired 2 revs forwards.
I tried a debounce after each button push, suspecting that button 2 may be incorrectly pressed twice, but any other combination of button pushes after a re-set works fine without a debounce, and after this initial incorrect 4 forward revs, then I can push buttons in any combination and the DC motor responds correctly and will never do the 4 revs again after pushing button #2.

I am using an Uno board,
using this motor driver board from Pololu: http://www.pololu.com/catalog/product/708
And this motor with encoder from pololu. http://www.pololu.com/catalog/product/1447

I admit to having a pretty poor level of understanding of everything that is going on in this code and I have tried a couple of things (for the last two days) based off hunches but to no avail.
The only thing that makes a change is if I change button #2 to only go 1 revolution, then the motor responds correctly to any combination of button pushes after a reset.
I tried to set up the serial read to help with trouble shooting, but soon realized I do not have the knowledge to set up variables to show my encoder direction and count #.

Below is my code, any suggestions or insight is appreciated.

Code:
// MD03A_Motor_basic + encoder
//credit to: KAS http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1282384853
//
#define InA1        10      // Pin 10, goes to Pololu INA motor direction pin (low forward, high reverse)
#define InB1        11      // Pin 11, goes to Pololu INB motor direction pin (low reverse, high forward)
#define PWM1        6       // Pin 6, goes to Pololu PWM pin (speed)
#define encodPinA1  3       // Pin 3, reads encoder A signal (yellow)
#define encodPinB1  8       // Pin 8, reads encoder B signal (White)
#define FORWARD     1       //
#define BACKWARD    2      //
#define buttonPin   A0      // Analog pin A0, reads Voltage of button 1, 2, or 3
//#define LOOPTIME    100     // PID loop time - what is this ?

unsigned long lastMilli = 0;       // loop timing
unsigned long lastMilliPrint = 0;  // loop timing
long count = 0;                   // rotation counter
long countInit;
long tickNumber = 0;
boolean run = false;         // motor moves
int buttonValue = 0;       // defines switchValue as an interger, sets value at 0 (of 0 -1000)
//

void setup() {
  pinMode(InA1, OUTPUT);           // direction to Pololu motor board
  pinMode(InB1, OUTPUT);           // direction to Pololu motor board
  pinMode(PWM1, OUTPUT);           // PWM output to Pololu motor board
  pinMode(encodPinA1, INPUT);      // input from encoder
  pinMode(encodPinB1, INPUT);      // input from encoder
  pinMode(buttonPin,INPUT);           // pin A0, reads V input from buttons
  digitalWrite(encodPinA1, HIGH);      // turn on pullup resistor pin 10
  digitalWrite(encodPinB1, HIGH);      // turn on pullup resistor pin 11
  attachInterrupt(1, rencoder, FALLING);
  Serial.begin(9600);                 // set up Serial library at 9600 bps
}

void loop() {

  buttonValue = analogRead(buttonPin);   // Read Voltage on pin A0
  if(buttonValue>940)                   // Button #1 470 resistor 992 max (1023=5v)
    moveMotor(FORWARD, 250, 2000*1);      // direction, PWM (speed), ticks number (2000=360°)

  buttonValue = analogRead(buttonPin);
  if(buttonValue>750 && buttonValue<800)  // Button #2 4.7k resistor  790 max, min = less than bttn #1
    moveMotor(FORWARD, 250, 2000*2);        // direction, PWM (speed), ticks number (2000=360°)   

  buttonValue = analogRead(buttonPin);
  if(buttonValue>600 && buttonValue<630)  // Button #3 10k resistor  620 max, min = less than bttn #2
    moveMotor(BACKWARD, 250, 2000*1);       // direction, PWM (speed), ticks number (2000=360°)

}
void moveMotor(int direction, int PWM_val, long tick)  {
  countInit = count;                                // abs(count)
  tickNumber = tick;
  if(direction==FORWARD)          motorForward(PWM_val);
  else if(direction==BACKWARD)    motorBackward(PWM_val);
}

void rencoder()  {                           // pulse and direction, direct port reading to save cycles
  if (PINB & 0b00000001)    count++;         // if(digitalRead(encodPinB1)==HIGH)   count_r ++;
  else                      count--;         // if(digitalRead(encodPinB1)==LOW)   count_r --;
  if(run) 
    if((abs(abs(count)-abs(countInit))) >= tickNumber)     
      motorBrake();
}

void motorForward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, LOW);
  digitalWrite(InB1, HIGH);
  run = true;
}

void motorBackward(int PWM_val)  {
  analogWrite(PWM1, PWM_val);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, LOW);
  run = true;
}

void motorBrake()  {
  analogWrite(PWM1, 0);
  digitalWrite(InA1, HIGH);
  digitalWrite(InB1, HIGH);
  run = false;
}
Pages: [1]