Sie sind auf Seite 1von 5

DC Motor Bidirectional Speed Control Using

PWM
This mini-project explains the use of PIC16F877A internal PWM module to control the speed of a DC
motor, it also describes the use of H-Bridge circuit to control the direction of rotation.

The Concept of Pulse-Width-Modulation (PWM) :


a square wave signal is described by three parameters, amplitude, frequency and duty cycle (AKA
pulse width).
The term "duty cycle" describes the ratio of the ON state of the signal to the period of that signal,
i.e. Duty = TON/T = TON/( TON+TOFF)
Duty cycle has no unit, its represented by percentage with 100% describing the fully ON state and
0% describing the fully OFF state.

PWM concerns about the duty cycle of a square wave signal, it's the technique in which we change
the pulse width to get the desired duty cycle.

Speed Control Using PWM:


The idea of speed control is to switch the motor ON and OFF at varying speeds, let us say we have
a 12V DC motor and we applied a constant 12V signal to that motor, the motor would run in its full
power (full speed).
Now assume we apply a 50% duty cycle signal to the motor (at several KHz frequency), the motor
will turn ON and OFF continuously and the effective voltage applied to the motor is 6V, this would
decrease the motor speed by the half, and the motor would be running at 50% of it's full power.
Varying the duty cycle of the applied signal would cause the speed to vary, a 0% duty cycle signal
would turn OFF the motor, and a 100% one would run the motor at it's full speed.
The PIC16F877A PWM Module:
16F877a includes two PWM modules included in the CCP1,CCP2 modules (CCP stands for
Capture-Compare-PWM), and there are 3 steps for using those modules:
1. Set the desired CCP module to PWM mode.
2. Setup The TIMER2 module, which controls the frequency and the base of your PWM signal.
3. Set your duty cycle, rely on the equations below to select it properly.
We'll be using CCS PIC-C compiler to explain those steps, if you have a question on using other
compilers to set it, post a comment.
To set The CCP1 module to PWM mode, we'll use the code line:
setup_ccp1(CCP_PWM);
and the first step is done.
Now setting up Timer2 module using PIC-C is a bit easy, use the code line:
setup_timer_2(divider,preload,postscalar).
the divider and the preload values determines the frequency of the PWM signal by the following
function:
Signal Frequency = (Crystal/4) / (divider * (preload+1))
The divider takes the values : T2_DIV_BY_1, T2_DIV_BY_4, T2_DIV_BY_16.
the preload is 8Bits and takes the values 0-255
So let us say we have 4MHz crystal and we set Timer2 like this:
setup_timer_2( T2_DIV_BY_1, 255, 1);
thus, our signal frequency is (4MHz/1)/(4 * 256) = 3.9KHz

Now the final step is to set your duty cycle using the function: set_pwm1_duty(duty_parameter);
to get the duty_parameter of your desired duty cycle, note the following:
the maximum value of duty_paramter (MAX) = ((preload+1)*4) -1
so in our case the maximum value is ((255+1)*4)-1 = 1023 and it represents a 100% duty cycle.
now if we need a duty cycle of 50% it would be 1023*0.5 = 512, and a duty cycle of 25% would be
1023*0.25 = 256, thus,

set_pwm1_duty(1023L); ---> 100% duty (Full Speed)


set_pwm1_duty(512L); ----> 50% duty
set_pwm1_duty(256L); ----> 25% duty
set_pwm1_duty(0); ----> 0% duty (OFF)

Note: the capital letter L at the end of the parameter instructs the compiler to treat the number as
Long integer.

The H-Bridge and the Direction of Rotation:


L298 is a dual H-Bridge transistor circuitry used to isolate and control DC Motors, Micrcontrollers has
current limitations so it can't drive a high power element such as a motor, the H-Bridge solves the
problem by providing a different power supply for driving the motors.
For a single motor connected to OUT1,OUT2 respectively, the inputs IN1,IN2 controls the direction
of rotation, setting IN1=1 IN2=0 would rotate the motor clockwise, while setting IN1=0 IN2=1 would
rotate it counter clockwise, and the setting IN1=0 IN2=0 would turn it OFF.
The pin ENA (Enable motor A) is used turn ON/OFF the motor regardless of the inputs IN1 IN2,
thus, our PWM signal could be connected to ENA to control the speed of the motor.
The Schematic Design:

Buttons UP/Down are used to increase/decrease the speed (the duty cycle)
Button Direction is used to flip the direction of rotation (CW/CCW)
CCP1 Pin 17 carries the PWM signal and connected to the motor enable pin ENA
Diodes D1-D4 are free-wheeling diodes used to protect the circuit from reverse currents.
C1 is an electromagnetic interference elimination capacitor, to protect against voltage spikes.

The C-Code

/*
PIC16F877A and L298 H-Bridge Motor Speed/Direction Controller

Electronics Lovers
www.facebook.com/Electronics.loverz
*/

#include <16f877a.h>
#fuses XT,NOLVP,NOWDT,NOPROTECT
#use delay(clock=4000000)

#define Wire1 PIN_B6


#define Wire2 PIN_B7
#define Up PIN_A0
#define Down PIN_A1
#define Dir PIN_A2

int16 duty_cycle=512;

void main()
{
setup_adc(ADC_OFF); // Turn ADC OFF
setup_adc_ports(NO_ANALOGS); // All Ports are digital I/O
output_high(Wire1);
output_low(Wire2); // Set the motor to CW direction

/* PWM Configurations */
setup_timer_2(T2_DIV_BY_1,255,1); // Set PWM frequency
setup_ccp1(CCP_PWM); // Configure CCP1 to PWM mode
set_pwm1_duty(512L); // default duty cycle = 50% (Half Speed)

while(1)
{
while(input(Up) && input(Down) && input(Dir)); // Hold until a button is pressed

if(!input(Up)) // Button (Up) Selected?


{
duty_cycle+=64; // increase the duty cycle by some percentage (+6.25%)
set_pwm1_duty(duty_cycle); // set the duty cycle
}
if(!input(Down)) // Button (Down) Selected?
{
duty_cycle-=64; // decrease the duty cycle
set_pwm1_duty(duty_cycle); // set the duty cycle
}
if(!input(Dir)) // Button (Direction) Selected?
{
output_toggle(Wire1); // Toggle the polarity of IN1 IN2
output_toggle(Wire2); // 0 becomes 1 , 1 becomes 0
}

delay_ms(500); // 0.5 second delay to release the selected button


}
}
www.facebook.com/Electronics.loverz

Das könnte Ihnen auch gefallen