循迹小车原理介绍和代码示例

 目录

循迹小车 

1. 循迹模块使用

2. 循迹小车原理

3. 循迹小车开发和调试代码


循迹小车 

1. 循迹模块使用

  • TCRT5000传感器的红外发射二极管不断发射红外线
  • 当发射出的红外线没有被反射回来或被反射回来但强度不够大时
  • 红外接收管一直处于关断状态,此时模块的输出端为高电平,指示二极管一直处于熄灭状态
  • 被检测物体出现在检测范围内时,红外线被反射回来且强度足够大,红外接收管饱和
  • 此时模块的输出端为低电平,指示二极管被点亮
  • 总结就是一句话,没反射回来,D0输出高电平,灭灯

接线方式

  • VCC:接电源正极(3-5V)
  • GND:接电源负极 DO:TTL开关信号输出0、1
  • AO:模拟信号输出(不同距离输出不同的电压,此脚一般可以不接)

2. 循迹小车原理

由于黑色具有较强的吸收能力,当循迹模块发射的红外线照射到黑线时,红外线将会被黑线吸收,导致 循迹模块上光敏三极管处于关闭状态,此时模块上一个LED熄灭。在没有检测到黑线时,模块上两个LED常亮

总结就是一句话,有感应到黑线,D0输出高电平 ,灭灯

3. 循迹小车开发和调试代码

//main.c
#include "motor.h"
#include "delay.h"
#include "uart.h"
#include "time.h"
#include "reg52.h"
extern char speedLeft;
extern char speedRight;


sbit leftSensor = P2^7;
sbit rightSensor = P2^6;

void main()
{
	Time0Init();
	Time1Init();
	//UartInit();
	
	while(1){
		
		if(leftSensor == 0 && rightSensor == 0){
				speedLeft = 32;
				speedRight = 40;
		}
		if(leftSensor == 1 && rightSensor == 0){
				speedLeft = 12;//10份单位时间全速运行,30份停止,所以慢,20ms是40份的500us
				speedRight = 40;
		}
		
		if(leftSensor == 0 && rightSensor == 1){
				speedLeft = 32;
				speedRight = 20;
		}
		
		if(leftSensor == 1 && rightSensor == 1){
			//停
				speedLeft = 0;
				speedRight = 0;
		}
	}
}

//motor.c
#include "reg52.h"

sbit RightCon1A = P3^2;
sbit RightCon1B = P3^3;

sbit LeftCon1A = P3^4;
sbit LeftCon1B = P3^5;

void goForwardLeft()
{
	LeftCon1A = 0;
	LeftCon1B = 1;
}

void stopLeft()
{
	LeftCon1A = 0;
	LeftCon1B = 0;
}

void goForwardRight()
{
	RightCon1A = 0;
	RightCon1B = 1;
}
void stopRight()
{
	RightCon1A = 0;
	RightCon1B = 0;
}



void goForward()
{
	LeftCon1A = 0;
	LeftCon1B = 1;
	
	RightCon1A = 0;
	RightCon1B = 1;
}

void goRight()
{
	LeftCon1A = 0;
	LeftCon1B = 1;
	
	RightCon1A = 0;
	RightCon1B = 0;
}


void goLeft()
{
	LeftCon1A = 0;
	LeftCon1B = 0;
	
	RightCon1A = 0;
	RightCon1B = 1;
}

void goBack()
{
	LeftCon1A = 1;
	LeftCon1B = 0;
	
	RightCon1A = 1;
	RightCon1B = 0;
}

void stop()
{
	LeftCon1A = 0;
	LeftCon1B = 0;
	
	RightCon1A = 0;
	RightCon1B = 0;
}

//delay.c
#include "intrins.h"

void Delay1000ms()		//@11.0592MHz
{
	unsigned char i, j, k;

	_nop_();
	i = 8;
	j = 1;
	k = 243;
	do
	{
		do
		{
			while (--k);
		} while (--j);
	} while (--i);
}



//time.c
#include "motor.h"
#include "reg52.h"

char speedLeft;
char cntLeft = 0;

char speedRight;
char cntRight = 0;

void Time1Init()
{
	//1. 配置定时器1工作模式位16位计时
	TMOD &= 0x0F;
	TMOD |= 0x1 << 4;
	//2. 给初值,定一个0.5出来
	TL1=0x33;
	TH1=0xFE;
	//3. 开始计时
	TR1 = 1;
	TF1 = 0;
	//4. 打开定时器1中断
	ET1 = 1;
	//5. 打开总中断EA
	EA = 1;
}


void Time0Init()
{
	//1. 配置定时器0工作模式位16位计时
	TMOD = 0x01;
	//2. 给初值,定一个0.5出来
	TL0=0x33;
	TH0=0xFE;
	//3. 开始计时
	TR0 = 1;
	TF0 = 0;
	//4. 打开定时器0中断
	ET0 = 1;
	//5. 打开总中断EA
	EA = 1;
}

void Time1Handler() interrupt 3
{
	cntRight++;  //统计爆表的次数. cnt=1的时候,报表了1
	//重新给初值
	TL1=0x33;
	TH1=0xFE;
	
	//控制PWM波
	if(cntRight < speedRight){
		//右前进
		goForwardRight();
	}else{
		//停止
		stopRight();
	}
	
	if(cntRight == 40){//爆表40次,经过了20ms
		cntRight = 0;  //当100次表示1s,重新让cnt从0开始,计算下一次的1s
	}
		
}

void Time0Handler() interrupt 1
{
	cntLeft++;  //统计爆表的次数. cnt=1的时候,报表了1
	//重新给初值
	TL0=0x33;
	TH0=0xFE;
	
	//控制PWM波
	if(cntLeft < speedLeft){
		//左前进
		goForwardLeft();
	}else{
		//停止
		stopLeft();
	}
	
	if(cntLeft == 40){//爆表40次,经过了20ms
		cntLeft = 0;  //当100次表示1s,重新让cnt从0开始,计算下一次的1s
	}
		
}

猜你喜欢

转载自blog.csdn.net/m0_74712453/article/details/132717022