Hardware components | ||||||
| × | 1 | ||||
Software apps and online services | ||||||
![]() |
|
Video:
1 / 20
// ****************************************************************
// line_follower.c - For line follower robot
// Author: Ajaya Dahal - ad2323@msstate.edu
// ****************************************************************
#include "pic24_all.h"
// Define the time, in us, between Timer2 and Timer3 interrupts to generate PWM of 1KHz.
#define ISR_PERIOD (1000)
//MOTOR Enable
#define CONFIG_MOTOR1_EN() CONFIG_RB3_AS_DIG_OUTPUT()
#define CONFIG_MOTOR2_EN() CONFIG_RB4_AS_DIG_OUTPUT()
#define MOTOR_1_EN (_LATB3)
#define MOTOR_2_EN (_LATB4)
//left motor
#define CONFIG_MOTOR1_A() CONFIG_RB5_AS_DIG_OUTPUT()
#define CONFIG_MOTOR1_B() CONFIG_RB6_AS_DIG_OUTPUT()
#define MOTOR_1_A (_LATB5)
#define MOTOR_1_B (_LATB6)
//right_motor
#define CONFIG_MOTOR2_A() CONFIG_RB13_AS_DIG_OUTPUT()
#define CONFIG_MOTOR2_B() CONFIG_RB14_AS_DIG_OUTPUT()
#define MOTOR_2_A (_LATB13)
#define MOTOR_2_B (_LATB14)
//setup sensors
#define CONFIG_SENSOR_A() CONFIG_RB0_AS_DIG_INPUT()
#define CONFIG_SENSOR_B() CONFIG_RB1_AS_DIG_INPUT()
#define ENABLE_SENSOR_A() ENABLE_RB0_PULLDOWN()
#define ENABLE_SENSOR_B() ENABLE_RB1_PULLDOWN()
#define SENSOR_A (_RB0)
#define SENSOR_B (_RB1)
//function to move forward
void move_forward(void){
MOTOR_1_A = 1;
MOTOR_1_B = 0;
MOTOR_2_A = 1;
MOTOR_2_B = 0;
}
//function to stop motor
void stop_motors(void){
//disable the enable pin will stop motor
MOTOR_1_EN = 0;
MOTOR_2_EN = 0;
}
//function to turn left
void move_left(void){
MOTOR_1_A = 0;
MOTOR_1_B = 0;
MOTOR_2_A = 1;
MOTOR_2_B = 0;
}
//function to turn right
void move_right(void){
MOTOR_1_A = 1;
MOTOR_1_B = 0;
MOTOR_2_A = 0;
MOTOR_2_B = 0;
}
//function to move reverse NOT IMPLEMENTED but for future use
void move_reverse(void){
MOTOR_1_A = 1;
MOTOR_1_B = 0;
MOTOR_2_A = 1;
MOTOR_2_B = 0;
}
//config motor pins
void configMotors(void){
CONFIG_MOTOR1_EN();
CONFIG_MOTOR2_EN();
CONFIG_MOTOR1_A();
CONFIG_MOTOR1_B();
CONFIG_MOTOR2_A();
CONFIG_MOTOR2_B();
}
//config sensor pins
void configSensors(void){
CONFIG_SENSOR_A();
CONFIG_SENSOR_B();
ENABLE_SENSOR_A();
ENABLE_SENSOR_B();
}
//create PWM for left motor
void createPWM_Left(void){
//700+300 = 1000us = 1ms results in 1KHz PWM with 30% duty cycle.
if (MOTOR_1_EN == 1) {
PR2 = usToU16Ticks(700, getTimerPrescale(T2CONbits)) - 1;
MOTOR_1_EN = 0;
} else {
PR2 = usToU16Ticks(300, getTimerPrescale(T2CONbits)) - 1;
MOTOR_1_EN = 1;
}
}
//create PWM for right motor
void createPWM_Right(void){
//700+300 = 1000us = 1ms results in 1KHz PWM with 30% duty cycle.
if (MOTOR_2_EN == 1) {
PR3 = usToU16Ticks(700, getTimerPrescale(T3CONbits)) - 1;
MOTOR_2_EN = 0;
} else {
PR3 = usToU16Ticks(300, getTimerPrescale(T3CONbits)) - 1;
MOTOR_2_EN = 1;
}
}
// Interrupt Service Routine for Timer2 which is for LEFT motor
void _ISR _T2Interrupt(void) {
createPWM_Left();
// Clear the timer interrupt bit, signaling the PIC that this interrupt has been serviced.
_T2IF = 0;
}
// Interrupt Service Routine for Timer3 which is for RIGHT motor
void _ISR _T3Interrupt(void) {
createPWM_Right();
// Clear the timer interrupt bit, signaling the PIC that this interrupt has been serviced.
_T3IF = 0;
}
void configTimer2(void) {
T2CON = T2_OFF | T2_IDLE_CON | T2_GATE_OFF
| T2_32BIT_MODE_OFF
| T2_SOURCE_INT
| T2_PS_1_8;
// Subtract 1 from ticks value assigned to PR2 because period is PRx + 1.
PR2 = usToU16Ticks(ISR_PERIOD, getTimerPrescale(T2CONbits)) - 1;
// Start with a cleared timer2 value.
TMR2 = 0;
// Enable Timer2 interrupts.
_T2IF = 0;
_T2IP = 1;
_T2IE = 1;
// Start the timer only after all timer-related configuration is complete.
T2CONbits.TON = 1;
}
void configTimer3(void) {
T3CON = T3_OFF | T3_IDLE_CON | T3_GATE_OFF
| T3_SOURCE_INT
| T3_PS_1_8;
// Subtract 1 from ticks value assigned to PR2 because period is PRx + 1.
PR3 = usToU16Ticks(ISR_PERIOD, getTimerPrescale(T3CONbits)) - 1;
// Start with a cleared timer2 value.
TMR3 = 0;
// Enable Timer3 interrupts.
_T3IF = 0;
_T3IP = 1;
_T3IE = 1;
// Start the timer only after all timer-related configuration is complete.
T3CONbits.TON = 1;
}
//function that compares the sensors status and control the motor driver accordingly
void start_following(void){
if(!SENSOR_A && !SENSOR_B){
move_reverse();
}
else if(SENSOR_A && !SENSOR_B){
move_left();
}
else if(!SENSOR_A && SENSOR_B){
move_right();
}
else{
move_forward();
}
}
int main (void) {
configBasic(HELLO_MSG);
configMotors();
configSensors();
configTimer2();
configTimer3();
stop_motors();
while (1) {
start_following();
DELAY_MS(20);
stop_motors();
// Blink the heartbeat LED to show that the PIC is running.
doHeartbeat();
DELAY_MS(10);
}
}
11 projects • 15 followers
Electrical and Computer Engineering
Certified Part 107 FAA Drone Pilot
Comments
Please log in or sign up to comment.