Sunday, August 26, 2012

Arduino PWM Brushed DC motor Controller Part 1

It was in my schooling days over 2 decades ago when I first came across PWM (Pulse-Width Modulation). I am fascinated by how efficient it can be utilize in a myriad of power electronics application. The working principle is easy to understand but implementing isn't ... Well, at least to me at that point of time when anything that requires micro-processor is considered  alien technology or witch craft.... After all it was the age of 8086 XT & I was only a poor teenage student without internet & any common interest friends let alone finding any mentor to guide me in the pursuit...

Every now & than over the years,  I encounter numerous literature on microprocessor use in PWM thingy... Not that I'm a genius, but after over a decade of leisure reading, it has came to the point that I just had to have a go at it.

Personally, I consider Arduino is a blessing, it has everything I need to get it done. Without it, I would never had bothered tinkering with micro-controller.

The plan is to build an experimental DC motor controller with
1) Potential meter (POT) as Direction & Speed control dialing nob.
2) Arduino as the micro-controller.
3) ~16kHz PWM frequency to keep the motor running quiet

Here is the code I wrote. Short, but that is all that is required.


#include <avr/interrupt.h>

//Analog Pins Allocation
int POT_pin = 0; //Speed & direction control POT connect to A0

//Digital Pins Allocation
int IN1 = 7;  //Controller IN1 pin connect to D7 Pin
int IN2 = 8;  //Controller IN2 pin to connect D8 Pin
int INH = 9;  //INH1 & INH2 are common & comnect to PWM D9 Pin

// Variables

int Motor_speed = 0;  //Motor speed to achieve balancing

void setup() {

TCCR1A = B11110010;
TCCR1B = B00011001;

TCCR1B = 25;// 00011001
ICR1 = 1023 ; // 10 bit resolution
OCR1A = 511; // vary this value between 0 and 1024 for 10-bit precision
OCR1B = 511; // vary this value between 0 and 1024 for 10-bit precision

pinMode (IN1, OUTPUT);
pinMode (IN2, OUTPUT);
pinMode (INH, OUTPUT);    //PWM Analog
}
void loop()
{
  Motor_speed = map(analogRead(POT_pin),0,1024,-1023,1023);
if (Motor_speed>0)
  {
    digitalWrite(IN1,HIGH);
    digitalWrite(IN2,LOW);
  }
  else
  {
    digitalWrite(IN1,LOW);
    digitalWrite(IN2,HIGH);
  }

  analogWrite(INH,(1023-abs(Motor_speed)));
//the "1023-" is there to correct the actual PWM percentage with respect to the POT

}


The required power electronics will come in Part 2...

1 comment: