智能小车系统设计循迹超声波遥控.docx
《智能小车系统设计循迹超声波遥控.docx》由会员分享,可在线阅读,更多相关《智能小车系统设计循迹超声波遥控.docx(25页珍藏版)》请在冰豆网上搜索。
![智能小车系统设计循迹超声波遥控.docx](https://file1.bdocx.com/fileroot1/2023-6/23/fa8ffa04-288c-440a-b09c-877ab9fcbf82/fa8ffa04-288c-440a-b09c-877ab9fcbf821.gif)
智能小车系统设计循迹超声波遥控
<<计算机控制技术综合训练>>任务书
年季学期
学生姓名
学号
专业方向
班级
题目名称
智能小车系统设计2
一、设计内容及技术要求:
(一)、任务描述
利用《智能小车系统设计2》所提供部件(综合训练目前共有3种智能小车模型),组装小车模型,编写检测、控制程序,实现以单片机为控制系统核心的智能小车系统设计。
(二)、控制任务和要求
基本任务:
1.完成小车的组装工作
2.小车可完成前进、后退、左转、右转等动作,并且可以正确显示当前的速度及行进位移
3.小车具有循迹(自己设计跑道)及避障功能
4.三周设计任务完成后,不必拆分小车,将小车归还老师并如实汇报功能部件运转情况,便于老师及时维护,为下一组同学的设计做好准备
进阶任务:
1.实现舵机转动下的超声波壁障功能,并且可以正确显示前方物体的距离
2.与按键功能配合,正确有序显示小车位移、速度及与前方障碍物距离
3.小车具有无线遥控功能
4.与其它组的小车模型配合可以完成交替领跑任务
二、课程设计总结报告要求:
1.完整的设计任务书:
封面(设计题目、指导教师、专业班级、姓名、学号、时间);
摘要及关键词(3~5):
设计总体概述(采用何种硬件,利用何种方法,设计何种东西,实现了何种功能)
目录(按目录格式书写,页码要标清)
第一章绪言(本设计的内容与实现的基本原理,设计的特点及可以最终可以实现的功能,可以达到的性能指标)
第二章方案论证(对所提供的硬件理解并画出系统结构图,为实现该任务所采取软件设计思路及核心算法)
第三章硬件设计(按照结构框图对各功能部分进行分别介绍,如系统CPU部分、数据采集部分、程序控制部分、人机接口部分等)
第四章软件设计(整体设计思路,各独立程序功能、原理介绍包括流程图,如主程序、各子程序及中断服务程序)
第五章设计总结(对整个设计过程的总结、体会,还包括设计中遇到的问题及解决的办法,以及想要实现却未能完成的功能)
参考文献:
著作格式:
作者.书名.版次.出版地:
出版者,出版年;
期刊格式:
作者.文章名.期刊名,年,卷(期):
起止页
注:
字数10000字左右,不得抄袭和雷同,使用学生作业纸(16开)
2.手绘硬件连接2#图一张、手绘软件流程2#图一张。
三、设计进度:
第一周:
熟悉掌握系统要求,完成硬件设计、调试。
第二周:
完成软件设计,用仿真器完成软、硬件联调,最终实现单片机在目标系统中的
合理运行
第三周:
完善设计,完成说明书编写,答辩。
指导教师签字:
附录:
电信学院课程设计报告要求
1、设计题目;
2、目录;
3、本设计的基本原理;
4、简要说明本设计内容、用途及特点;
5、本设计达到的性能指标;
6、设计方案的选择;
7、写出各部分设计过程、工作原理、元器件选择;
8、绘制图纸(手绘2号图纸);
9、设计参考文献;
10、附录;
11、设计总结体会;
12、设计说明书不得少于10000字。
智能小车运行图
显示速度,距离,超声波探测距离
经过调试,小车完美实现了如下功能
1.小车具有无线遥控功能,小车可完成前进、后退、左转、右转等动作,并且可以正确显示当前的速度及行进位移。
2.小车具有循迹及避障功能,实现了舵机转动下的超声波壁障功能,并且可以正确有序显示小车位移、速度及与前方障碍物距离。
3.与其它组的小车模型配合可以完成交替领跑任务。
4.小车所有模式切换均由遥控器控制。
流程图
硬件原理图
附件一:
智能小车系统程序
#include
#include
sbitAA=P3^0;
sbitDD=P3^1;
sbitBB=P3^2;
sbitCC=P2^2;
sbitLCM_RW=P2^4;//定义LCD引脚
sbitLCM_RS=P2^3;
#defineRXP2_0
#defineTXP2_1
#defineLCM_EP2_5
#defineSevro_moto_pwmP2_7//接舵机信号端输入PWM信号调节速度
#defineLCM_DataP0
#defineBusy0x80//用于检测LCM状态字中的Busy标识
#defineLeft_1_ledP3_7//P3_7接四路寻迹模块接口第一路输出信号即中控板上面标记为OUT1
#defineXUNJI_left_ledP3_6//P3_6接四路寻迹模块接口第二路输出信号即中控板上面标记为OUT2
#defineXUNJI_right_ledP3_5//P3_5接四路寻迹模块接口第三路输出信号即中控板上面标记为OUT3
#defineRight_2_ledP3_4//P3_4接四路寻迹模块接口第四路输出信号即中控板上面标记为OUT4
#defineLeft_moto_go{P1_4=1,P1_5=0,P1_6=1,P1_7=0;}//左边两个电机向前走
#defineLeft_moto_back{P1_4=0,P1_5=1,P1_6=0,P1_7=1;}//左边两个电机向后转
#defineLeft_moto_Stop{P1_4=0,P1_5=0,P1_6=0,P1_7=0;}//左边两个电机停转
#defineRight_moto_go{P1_0=1,P1_1=0,P1_2=1,P1_3=0;}//右边两个电机向前走
#defineRight_moto_back{P1_0=0,P1_1=1,P1_2=0,P1_3=1;}//右边两个电机向后走
#defineRight_moto_Stop{P1_0=0,P1_1=0,P1_2=0,P1_3=0;}//右边两个电机停转
voidLCMInit(void);//LCD初始化函数
voidDisplayOneChar(unsignedcharX,unsignedcharY,unsignedcharDData);
//LCD显示一个字符函数
voidDisplayListChar(unsignedcharX,unsignedcharY,unsignedcharcode*DData);//LCD显示一个字符串函数
voidDelay5Ms(void);//延时5毫秒函数
voidDelay400Ms(void);//延时400毫秒函数
voidDecode(unsignedcharScanCode);
voidWriteDataLCM(unsignedcharWDLCM);//LCD1602写数据函数
voidWriteCommandLCM(unsignedcharWCLCM,BuysC);//LCD写命令函数
unsignedcharReadStatusLCM(void);
unsignedcharcodeRange[]="V=cm/sS=.m";//LCD1602显示格式
unsignedcharcodewelcome[]="===Welcome===";
unsignedcharcodekey[]="Pressanykey...";
unsignedcharcodeASCII[13]="0123456789.-M";
unsignedcharcodetable[]="Distance:
000.0cm";
unsignedcharcodetable1[]="YAOKONGMOSHI";
unsignedcharcodetable2[]="=XUNJIMOSHI=";
unsignedcharpwm_val_left=0;//变量定义
unsignedcharpush_val_left=14;//舵机归中,产生约,1.5MS信号
unsignedintCH0=0;//循迹模式标志
unsignedintCH1=0;//超声波模式标志
unsignedintt=0;//速度基准变量
unsignedinttimer=0;//延时基准变量
unsignedinttime=0;
unsignedintpwm=250;
unsignedintcount1=0;//计左电机码盘脉冲值
unsignedchartimer1=0;//扫描时间变量
unsignedlongS1=0;
unsignedlongS2=0;
unsignedlongS3=0;
unsignedlongS4=0;
unsignedlongS=0;
unsignedlongV=0;//定义其速度
unsignedlongSS=0;
unsignedchardisbuff[4]={0,0,0,0,};
unsignedchardisbuff1[4]={0,0,0,0,};
voidWriteDataLCM(unsignedcharWDLCM)//写数据
{
ReadStatusLCM();//检测忙
LCM_Data=WDLCM;
LCM_RS=1;
LCM_RW=0;
LCM_E=0;//若晶振速度太高可以在这后加小的延时
LCM_E=0;//延时
LCM_E=1;
}
voidWriteCommandLCM(unsignedcharWCLCM,BuysC)//写指令,BuysC为0时忽略忙检测
{
if(BuysC)ReadStatusLCM();//根据需要检测忙
LCM_Data=WCLCM;
LCM_RS=0;
LCM_RW=0;
LCM_E=0;
LCM_E=0;
LCM_E=1;
}
unsignedcharReadStatusLCM(void)//读状态
{
LCM_Data=0xFF;
LCM_RS=0;
LCM_RW=1;
LCM_E=0;
LCM_E=0;
LCM_E=1;
while(LCM_Data&Busy);//检测忙信号
return(LCM_Data);
}
voidLCMInit(void)//LCM初始化
{
LCM_Data=0;
WriteCommandLCM(0x38,0);//三次显示模式设置,不检测忙信号
Delay5Ms();
WriteCommandLCM(0x38,0);
Delay5Ms();
WriteCommandLCM(0x38,0);
Delay5Ms();
WriteCommandLCM(0x38,1);//显示模式设置,开始要求每次检测忙信号
WriteCommandLCM(0x08,1);//关闭显示
WriteCommandLCM(0x01,1);//显示清屏
WriteCommandLCM(0x06,1);//显示光标移动设置
WriteCommandLCM(0x0c,1);//显示开及光标设置
}
//按指定位置显示一个字符
voidDisplayOneChar(unsignedcharX,unsignedcharY,unsignedcharDData)
{
Y&=0x1;
X&=0xF;//限制X不能大于15,Y不能大于1
if(Y)X|=0x40;//当要显示第二行时地址码+0x40;
X|=0x80;//算出指令码
WriteCommandLCM(X,1);//发命令字
WriteDataLCM(DData);//发数据
}
//按指定位置显示一串字符
voidDisplayListChar(unsignedcharX,unsignedcharY,unsignedcharcode*DData)
{
unsignedcharListLength;
ListLength=0;
Y&=0x1;
X&=0xF;//限制X不能大于15,Y不能大于1
while(DData[ListLength]>0x19)//若到达字串尾则退出
{
if(X<=0xF)//X坐标应小于0xF
{
DisplayOneChar(X,Y,DData[ListLength]);
//显示单个字符
ListLength++;
X++;
}
}
}
//5ms延时
voidDelay5Ms(void)
{
unsignedintTempCyc=5552;
while(TempCyc--);
}
//400ms延时
voidDelay400Ms(void)
{
unsignedcharTempCycA=5;
unsignedintTempCycB;
while(TempCycA--)
{
TempCycB=7269;
while(TempCycB--);
};
}
/********************************************************/
voidConut(void)//超声波距离计算函数
{
while(!
RX);//当RX为零时等待
TR0=1;//开启计数
while(RX);//当RX为零时等待
TR0=0;
time=TH0*256+TL0;
TH0=0;
TL0=0;
S=(time*1.7)/10+10;
disbuff1[0]=V%10;
disbuff1[1]=V/10;
DisplayListChar(0,0,Range);
DisplayOneChar(2,0,ASCII[disbuff1[1]]);
DisplayOneChar(3,0,ASCII[disbuff1[0]]);
disbuff1[0]=SS/10%10;
disbuff1[1]=SS/100%10;
disbuff1[2]=SS/1000;
DisplayOneChar(11,0,ASCII[disbuff1[2]]);
DisplayOneChar(12,0,ASCII[disbuff1[1]]);
DisplayOneChar(13,1,ASCII[10]);
DisplayOneChar(14,0,ASCII[disbuff1[0]]);
disbuff[0]=S%10;
disbuff[1]=S/10%10;
disbuff[2]=S/100%10;
disbuff[3]=S/1000;
DisplayListChar(0,1,table);
DisplayOneChar(9,1,ASCII[disbuff[3]]);
DisplayOneChar(10,1,ASCII[disbuff[2]]);
DisplayOneChar(11,1,ASCII[disbuff[1]]);
DisplayOneChar(12,1,ASCII[10]);
DisplayOneChar(13,1,ASCII[disbuff[0]]);
}
/********************************************************/
voidConut0(void)//循迹模式显示
{
disbuff1[0]=V%10;
disbuff1[1]=V/10;
DisplayListChar(0,0,Range);
DisplayOneChar(2,0,ASCII[disbuff1[1]]);
DisplayOneChar(3,0,ASCII[disbuff1[0]]);
disbuff1[0]=SS/10%10;
disbuff1[1]=SS/100%10;
disbuff1[2]=SS/1000;
DisplayOneChar(11,0,ASCII[disbuff1[2]]);
DisplayOneChar(12,0,ASCII[disbuff1[1]]);
DisplayOneChar(13,0,ASCII[10]);
DisplayOneChar(14,0,ASCII[disbuff1[0]]);
DisplayListChar(0,1,table2);
}
/********************************************************/
voidStartModule()//启动模块
{
TX=1;//启动一次模块
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
TX=0;
}
/********************************************************/
/*voiddelayms(unsignedintms)
{
unsignedchari=100,j;
for(;ms;ms--)
{
while(--i)
{
j=10;
while(--j);
}
}
}*/
voidTimer_Count(void)//超声波高电平脉冲宽度计算函数
{
TR0=1;//开启计数
while(RX);//当RX为1计数并等待
TR0=0;//关闭计数
Conut();//计算
}
/************************************************************************/
//前速前进
voidrun(void)
{
Left_moto_go;//左电机往前走
Right_moto_go;//右电机往前走
}
/************************************************************************/
//前速后退
voidbackrun(void)
{
Left_moto_back;//左电机往前走
Right_moto_back;//右电机往前走
}
/************************************************************************/
//左转
voidleftrun(void)
{
Left_moto_back;//左电机往前走
Right_moto_go;//右电机往前走
}
/************************************************************************/
//右转
voidrightrun(void)
{
Left_moto_go;//左电机往前走
Right_moto_back;//右电机往前走
}
/************************************************************************/
//STOP
voidstoprun(void)
{
Left_moto_Stop;//左电机停走
Right_moto_Stop;//右电机停走
}
/************************************************************************/
voidCOMM(void)
{
V=0;
push_val_left=5;//舵机向左转90度
timer=0;
while(timer<=4000);//延时400MS让舵机转到其位置4000
StartModule();//启动超声波测距
Conut();//计算距离
S2=S;
push_val_left=23;//舵机向右转90度
timer=0;
while(timer<=4000);//延时400MS让舵机转到其位置
StartModule();//启动超声波测距
Conut();//计算距离
S4=S;
push_val_left=14;//舵机归中
timer=0;
while(timer<=4000);//延时400MS让舵机转到其位置
StartModule();//启动超声波测距
Conut();//计算距离
S1=S;
if((S2<300)||(S4<300))//只要左右各有距离小于,30CM小车后退
{
backrun();//后退
timer=0;
while(timer<=1000);
}
if(S2>S4)
{
rightrun();//车的左边比车的右边距离小右转
timer=0;
while(timer<=800);
}
else
{
leftrun();//车的左边比车的右边距离大左转
timer=0;
while(timer<=800);
}
}
/****************************************************/
voidpwm_Servomoto(void)
{
if(pwm_val_left<=push_val_left)
Sevro_moto_pwm=1;
elseSevro_moto_pwm=0;
if(pwm_val_left>=100)
pwm_val_left=0;
}
/