標題:對于紅外循跡小車的進一步認知、組裝、與實驗運行,
1.對于模塊的重新準備,
這次選擇了更加便捷的四路循跡模塊,


2.四路循跡模塊安裝原理圖示


3.l289n電機安裝同上期一樣,需要空出循跡模塊的安裝位置進行相同的接線,
4.
(1)燒錄的程式
#-- coding:UTF-8 --
import RPi.GPIO as GPIO
import time
#小車電機引腳定義
IN1 = 20
IN2 = 21
IN3 = 19
IN4 = 26
ENA = 16
ENB = 13
#小車按鍵定義
key = 8
#循跡紅外引腳定義
#TrackSensorLeftPin1 TrackSensorLeftPin2 TrackSensorRightPin1 TrackSensorRightPin2
3 5 4 18
TrackSensorLeftPin1 = 3 #定義左邊第一個循跡紅外傳感器引腳為3口
TrackSensorLeftPin2 = 5 #定義左邊第二個循跡紅外傳感器引腳為5口
TrackSensorRightPin1 = 4 #定義右邊第一個循跡紅外傳感器引腳為4口
TrackSensorRightPin2 = 18 #定義右邊第二個循跡紅外傳感器引腳為18口
#設定GPIO口為BCM編碼方式
GPIO.setmode(GPIO.BCM)
#忽略警告資訊
GPIO.setwarnings(False)
#電機引腳初始化為輸出模式
#按鍵引腳初始化為輸入模式
#尋跡引腳初始化為輸入模式
def init():
global pwm_ENA
global pwm_ENB
GPIO.setup(ENA,GPIO.OUT,initial=GPIO.HIGH)
GPIO.setup(IN1,GPIO.OUT,initial=GPIO.LOW)
GPIO.setup(IN2,GPIO.OUT,initial=GPIO.LOW)
GPIO.setup(ENB,GPIO.OUT,initial=GPIO.HIGH)
GPIO.setup(IN3,GPIO.OUT,initial=GPIO.LOW)
GPIO.setup(IN4,GPIO.OUT,initial=GPIO.LOW)
GPIO.setup(key,GPIO.IN)
GPIO.setup(TrackSensorLeftPin1,GPIO.IN)
GPIO.setup(TrackSensorLeftPin2,GPIO.IN)
GPIO.setup(TrackSensorRightPin1,GPIO.IN)
GPIO.setup(TrackSensorRightPin2,GPIO.IN)
#設定pwm引腳和頻率為2000hz
pwm_ENA = GPIO.PWM(ENA, 2000)
pwm_ENB = GPIO.PWM(ENB, 2000)
pwm_ENA.start(0)
pwm_ENB.start(0)
#小車前進
def run(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.HIGH)
GPIO.output(IN2, GPIO.LOW)
GPIO.output(IN3, GPIO.HIGH)
GPIO.output(IN4, GPIO.LOW)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車后退
def back(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.LOW)
GPIO.output(IN2, GPIO.HIGH)
GPIO.output(IN3, GPIO.LOW)
GPIO.output(IN4, GPIO.HIGH)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車左轉
def left(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.LOW)
GPIO.output(IN2, GPIO.LOW)
GPIO.output(IN3, GPIO.HIGH)
GPIO.output(IN4, GPIO.LOW)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車右轉
def right(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.HIGH)
GPIO.output(IN2, GPIO.LOW)
GPIO.output(IN3, GPIO.LOW)
GPIO.output(IN4, GPIO.LOW)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車原地左轉
def spin_left(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.LOW)
GPIO.output(IN2, GPIO.HIGH)
GPIO.output(IN3, GPIO.HIGH)
GPIO.output(IN4, GPIO.LOW)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車原地右轉
def spin_right(leftspeed, rightspeed):
GPIO.output(IN1, GPIO.HIGH)
GPIO.output(IN2, GPIO.LOW)
GPIO.output(IN3, GPIO.LOW)
GPIO.output(IN4, GPIO.HIGH)
pwm_ENA.ChangeDutyCycle(leftspeed)
pwm_ENB.ChangeDutyCycle(rightspeed)
#小車停止
def brake():
GPIO.output(IN1, GPIO.LOW)
GPIO.output(IN2, GPIO.LOW)
GPIO.output(IN3, GPIO.LOW)
GPIO.output(IN4, GPIO.LOW)
#按鍵檢測
def key_scan():
while GPIO.input(key):
pass
while not GPIO.input(key):
time.sleep(0.01)
if not GPIO.input(key):
time.sleep(0.01)
while not GPIO.input(key):
pass
#延時2s
time.sleep(2)
#try/except陳述句用來檢測try陳述句塊中的錯誤,
#從而讓except陳述句捕獲例外資訊并處理,
try:
init()
key_scan()
while True:
#檢測到黑線時循跡模塊相應的指示燈亮,埠電平為LOW
#未檢測到黑線時循跡模塊相應的指示燈滅,埠電平為HIGH
TrackSensorLeftValue1 = GPIO.input(TrackSensorLeftPin1)
TrackSensorLeftValue2 = GPIO.input(TrackSensorLeftPin2)
TrackSensorRightValue1 = GPIO.input(TrackSensorRightPin1)
TrackSensorRightValue2 = GPIO.input(TrackSensorRightPin2)
#四路循跡引腳電平狀態
# 0 0 X 0
# 1 0 X 0
# 0 1 X 0
#以上6種電平狀態時小車原地右轉
#處理右銳角和右直角的轉動
if (TrackSensorLeftValue1 == False or TrackSensorLeftValue2 == False) and TrackSensorRightValue2 == False:
spin_right(100, 100)
time.sleep(0.08)
#四路循跡引腳電平狀態
# 0 X 0 0
# 0 X 0 1
# 0 X 1 0
#處理左銳角和左直角的轉動
elif TrackSensorLeftValue1 == False and (TrackSensorRightValue1 == False or TrackSensorRightValue2 == False):
spin_left(100, 100)
time.sleep(0.08)
# 0 X X X
#最左邊檢測到
elif TrackSensorLeftValue1 == False:
spin_left(80, 80)
# X X X 0
#最右邊檢測到
elif TrackSensorRightValue2 == False:
spin_right(80, 80)
#四路循跡引腳電平狀態
# X 0 1 X
#處理左小彎
elif TrackSensorLeftValue2 == False and TrackSensorRightValue1 == True:
left(0,90)
#四路循跡引腳電平狀態
# X 1 0 X
#處理右小彎
elif TrackSensorLeftValue2 == True and TrackSensorRightValue1 == False:
right(90, 0)
#四路循跡引腳電平狀態
# X 0 0 X
#處理直線
elif TrackSensorLeftValue2 == False and TrackSensorRightValue1 == False:
run(100, 100)
#當為1 1 1 1時小車保持上一個小車運行狀態
except KeyboardInterrupt:
pass
pwm_ENA.stop()
pwm_ENB.stop()
GPIO.cleanup()
(2)
#include<reg52.h>
typedef unsigned int u16;
typedef unsigned char u8;
sbit ENA = P2^0; //右點機使能
sbit IN1 = P2^1; //為0右輪反轉
sbit IN2 = P2^2; //為0右輪正轉
sbit IN3 = P2^3; //為0左輪正轉
sbit IN4 = P2^4; //為0左輪反轉
sbit ENB = P2^5; //左電機使能
sbit left1 = P1^3;
sbit left2 = P1^2;
sbit right1 = P1^1;
sbit right2 = P1^0;
u8 PWMCnt1 = 0;
u8 PWMCnt2 = 0;
u8 cntPWM1 = 0;
u8 cntPWM2 = 0;
void Timer0Init();
void XunJi();
void main()
{
Timer0Init();
while(1)
{
XunJi();
}
}
// i = 1時, 大概延時10us
//void delay(u16 i)
//{
// while (i–);
//}
void Timer0Init()
{
TH0 = 0xFF;
TL0 = 0xA3;
TMOD &= 0xF0;
TMOD |= 0x01;
EA = 1;
ET0 = 1;
TR0 = 1;
}
void TurnRight1() //右轉
{
IN1 = 0; //右輪反轉
IN2 = 1;
IN3 = 0; //左輪正轉
IN4 = 1;
cntPWM1 = 70;
cntPWM2 = 55;
}
void TurnRight2() //右轉
{
IN1 = 0; //右輪反轉
IN2 = 1;
IN3 = 0; //左輪正轉
IN4 = 1;
cntPWM1 = 50;
cntPWM2 = 40;
}
void TurnLeft1() //左轉
{
IN1 = 1;
IN2 = 0; //右輪正轉
IN3 = 1;
IN4 = 0; //左輪反轉
cntPWM1 = 55;
cntPWM2 = 70;
}
void TurnLeft2() //左轉
{
IN1 = 1;
IN2 = 0; //右輪正轉
IN3 = 1;
IN4 = 0; //左輪反轉
cntPWM1 = 40;
cntPWM2 = 50;
}
void Forward() //前進
{
IN1 = 1;
IN2 = 0; //右輪正轉
IN3 = 0; //左輪正轉
IN4 = 1;
cntPWM1 = 40;
cntPWM2 = 40;
}
//void Backward() //后退
//{
// IN1 = 0; //右輪反轉
// IN2 = 1;
//
// IN3 = 1;
// IN4 = 0; //左輪反轉
// cntPWM1 = 30;
// cntPWM2 = 30;
//}
void Stop() //停止
{
IN1 = 0;
IN2 = 0;
IN3 = 0;
IN4 = 0;
}
void XunJi()
{
unsigned char flag = 0;
if((left1 == 0)&&(left2 == 0)&&(right1 == 0)&&(right2 == 0)) //0 0 0 0
flag = 0;
if((left1 == 0)&&(left2 == 0)&&(right1 == 0)&&(right2 == 1)) //0 0 0 1
flag = 1;
if((left1 == 0)&&(left2 == 0)&&(right1 == 1)&&(right2 == 0)) //0 0 1 0
flag = 0;
if((left1 == 0)&&(left2 == 0)&&(right1 == 1)&&(right2 == 1)) //0 0 1 1
flag = 1;
if((left1 == 0)&&(left2 == 1)&&(right1 == 0)&&(right2 == 0)) //0 1 0 0
flag = 0;
if((left1 == 0)&&(left2 == 1)&&(right1 == 0)&&(right2 == 1)) //0 1 0 1
flag = 4;
if((left1 == 0)&&(left2 == 1)&&(right1 == 1)&&(right2 == 0)) //0 1 1 0
flag = 0;
if((left1 == 0)&&(left2 == 1)&&(right1 == 1)&&(right2 == 1)) //0 1 1 1
flag = 1;
if((left1 == 1)&&(left2 == 0)&&(right1 == 0)&&(right2 == 0)) //1 0 0 0
flag = 3;
if((left1 == 1)&&(left2 == 0)&&(right1 == 0)&&(right2 == 1)) //1 0 0 1
flag = 0;
if((left1 == 1)&&(left2 == 0)&&(right1 == 1)&&(right2 == 0)) //1 0 1 0
flag = 2;
// ?
if((left1 == 1)&&(left2 == 0)&&(right1 == 1)&&(right2 == 1)) //1 0 1 1
flag = 0;
if((left1 == 1)&&(left2 == 1)&&(right1 == 0)&&(right2 == 0)) //1 1 0 0
flag = 3;
//?
if((left1 == 1)&&(left2 == 1)&&(right1 == 0)&&(right2 == 1)) //1 1 0 1
flag = 0;
if((left1 == 1)&&(left2 == 1)&&(right1 == 1)&&(right2 == 0)) //1 1 1 0
flag = 3;
if((left1 == 1)&&(left2 == 1)&&(right1 == 1)&&(right2 == 1)) //1 1 1 1
flag = 5;
switch(flag)
{
case 0:Forward();break;
case 1:TurnRight1();break;
case 2:TurnRight2();break;
case 3:TurnLeft1();break;
case 4:TurnLeft2();break;
default:Stop();break;
}
}
void InterruptTime0() interrupt 1
{
PWMCnt1++;
PWMCnt2++;
if(PWMCnt1 >= 200)
{
PWMCnt1 = 0;
}
if(PWMCnt1 <= cntPWM1)
{
ENA = 1;
}
else
{
ENA = 0;
}
if(PWMCnt2 >= 200)
{
PWMCnt2 = 0;
}
if(PWMCnt2 <= cntPWM2)
{
ENB = 1;
}
else
{
ENB = 0;
}
TH0 = (65536 - 50)/256;
TL0 = (65536 - 50)%256;
}
物體完成,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/230990.html
標籤:其他
上一篇:單片機補充案例--中斷到呼叫不用
下一篇:java中多執行緒的創建方式一:
