智能小车的四路避障C程序.docx
《智能小车的四路避障C程序.docx》由会员分享,可在线阅读,更多相关《智能小车的四路避障C程序.docx(9页珍藏版)》请在冰豆网上搜索。
智能小车的四路避障C程序
智能小车的四路避障C程序
默认分类 2009-08-2410:
35 阅读164 评论4
字号:
大大 中中 小小
前,左,后避障传感器现在对应中,右,左三路寻线传感器.
#include
#include
#include"STC12C5410AD.H"
#include"sio.h"
#defineMIN9MS0x0120 //9ms中心是0x0159
#defineMAX9MS0x01a0
#defineMIN45MS0x0090 //4.5ms中心是0x00ac
#defineMAX45MS0x00d0
#defineMIN225MS0x0040 //2.25ms中心是0x0056
#defineMAX225MS0x0080
#defineMIN056MS0x000e //0.56ms中心是0x0015
#defineMAX056MS0x001b
#defineMIN168MS0x0020 //1.68ms中心是0x0040
#defineMAX168MS0x0060
sfrISP_CUNTR=0xE7;
sbitLED1=P1^1;
sbitLED2=P1^2;
sbitIR_FRONT=P3^3;
sbitIR_LEFT=P3^4;
sbitIR_RIGHT=P3^5;
sbitIR_BACK=P1^3;
sbitIR_OUT=P1^0;
sbitPWM0=P3^7;
sbitMOTO_IN_A1=P1^7;
sbitMOTO_IN_A2=P1^6;
sbitMOTO_IN_B1=P1^5;
sbitMOTO_IN_B2=P1^4;
bitpower_stat;
staticunsignedcharcar_stat;//小车状态:
0,停止;1,前进;2,后退;3,左转;4,右转;ff,自控寻线模式
staticunsignedcharcodeled_mod_table[3][20]={
{1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},
{1,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0},
{1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0}
};
unsignedcharidataled_mod=0;
staticunsignedcharidataled_tick=0;
staticunsignedcharidataled_ptr=0;
#defineIR_SIGNAL_TOTAL21
#defineIR_SIGNAL_VALID18
staticunsignedcharcodeir_table[IR_SIGNAL_TOTAL]={
1,1,1,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0
};
staticunsignedcharcodeir_check_table[IR_SIGNAL_TOTAL]={
0,0,0,0,1,1,1,0,0,0,0,0,0,1,1,1,1,0,0,0,0
};
staticunsignedcharidatair_ptr=0;
staticunsignedcharidatafront_signal=0;
staticunsignedcharidataback_signal=0;
staticunsignedcharidataleft_signal=0;
staticunsignedcharidataright_signal=0;
staticbitfront_obj=0,back_obj=0,left_obj=0,right_obj=0;
staticvoiddelay(unsignedlongv){
while(v--){
}
}
/*
*PCA中断计数,根据位置判断信号区域和定义,位置0表示初始,1代表引导码信号,2表示引导码间隔,
*3表示第一个bit的信号,4表示第一个bit的间隔,以次类推...
*更具体见对应的红外线协议.
*/
staticunsignedcharidatapca_tick;
staticunsignedcharidatapca_int_count;
staticunsignedchardatapca_int_total; /*根据引导头确定总长度*/
staticunsignedintidataperiod; /*红外信号占或空周期计数*/
staticunsignedcharidatadata_buf[6];/*红外线协议数据缓冲区*/
staticunsignedintidataccap1; //PCA0上一次的的计数
staticunsignedcharidataframe_dog;//红外帧看门狗,限定时间未接收完成清除工作
voidtime0_isr()interrupt1
{
unsignedchartmp;
if(ir_table[ir_ptr++]){
IR_OUT=0;
}else{
IR_OUT=1;
}
ir_ptr%=IR_SIGNAL_TOTAL;
tmp=ir_check_table[ir_ptr];
if((!
IR_FRONT&&tmp)||(IR_FRONT&&!
tmp))
front_signal++;
if((!
IR_LEFT&&tmp)||(IR_LEFT&&!
tmp))
left_signal++;
if((!
IR_RIGHT&&tmp)||(IR_RIGHT&&!
tmp))
right_signal++;
if((!
IR_BACK&&tmp)||(IR_BACK&&!
tmp))
back_signal++;
if(ir_ptr==0){
// com_putchar(front_signal);
if(front_signal>=IR_SIGNAL_VALID)
front_obj=1;
else
front_obj=0;
if(back_signal>=IR_SIGNAL_VALID)
back_obj=1;
else
back_obj=0;
if(left_signal>=IR_SIGNAL_VALID)
left_obj=1;
else
left_obj=0;
if(right_signal>=IR_SIGNAL_VALID)
right_obj=1;
else
right_obj=0;
front_signal=0;
back_signal=0;
left_signal=0;
right_signal=0;
}
}
voidtime0_initialize(void)
{
TMOD&=~0x0F; /*cleartimer0modebits*/
TMOD|=0x02; /*puttimer0intoMODE2*/
TH0=0x5C; /*256-XTAL*dur/T1_12/1000000,dur=定时器的周期,以us为单位*/
TL0=0x5C; /*100us*/
PT0=0; /*时钟0中断低优先级*/
TR0=1;
ET0=1;
}
staticvoidwakeup(void)interrupt2
{
}
staticvoidpca_isr(void)interrupt6
{
unsignedchari,j;
if(CCF1){
CCF1=0; //清PCA1中断标志
LED1=IR_RIGHT;
LED2=IR_RIGHT;
if(!
pca_int_count){ //第一次收到信号
if(!
IR_RIGHT){
ccap1=pca_tick*256+CCAP1H;
pca_int_count++;
}
}else{ //已经收到一些信号
period=pca_tick*256+CCAP1H-ccap1;
ccap1=pca_tick*256+CCAP1H;
//com_putchar(period/256);
//com_putchar(period%256);
if(pca_int_count==1){
if(periodMAX9MS){//9ms
pca_int_count=0;
frame_dog=0;
}else
pca_int_count++;
}elseif(pca_int_count==2){
if(period>MIN225MS&&period pca_int_total=3;
pca_int_count++;
}elseif(period>MIN45MS&&period pca_int_total=67;
pca_int_count++;
}else{
pca_int_count=0;
frame_dog=0;
}
}else{
if(IR_RIGHT){
if(period>MIN056MS&&period if(pca_int_count>=pca_int_total){//帧接收完毕,下面进行有效分析.
if(pca_int_total==67){//完整信号,含有引导信号,设备码8bit,设备反码8bit,命令字8bit,命令字反码8bit
if((data_buf[0]^data_buf[1]==0xff)&&(data_buf[2]^data_buf[3]==0xff)){
com_putchar(data_buf[0]);
com_putchar(data_buf[2]);
if(data_buf[0]==0x40){
switch(data_buf[2]){
case0x5F:
//左
car_stat=3;
break;
case0x5B:
//右
car_stat=4;
break;
case0x5A:
//上
car_stat=1;
break;
case0x5E:
//下
car_stat=2;
break;
case0x56:
//菜单
car_stat=0;
break;
case0x0:
//数字0
car_stat=0xff;
break;
case0x12:
//POWER
//power_stat=~power_stat;
break;
default:
break;
}
}
}
}else{ //重复信号,仅含有引导信号
}
pca_int_count=0;
frame_dog=0;
}else{
pca_int_count++;
}
}else{
pca_int_count=0;
frame_dog=0;
}
}else{
j=(pca_int_count-3)/2;
i=j/8;
j=j%8;
if(period>MIN168MS&&period // com_putchar(0x01);
data_buf|=(0x01< pca_int_count++;
}elseif(period>MIN056MS&&period // com_putchar(0x00);
data_buf&=~(0x01< pca_int_count++;
}else{
pca_int_count=0;
frame_dog=0;
}
}
}
}
}
if(CF){ //PCA计数溢出中断,19.6608MHZ晶体大约6.7ms溢出
CF=0;
pca_tick++;
if(led_tick++>=10){
led_tick=0;
if(led_mod_table[led_mod][led_ptr++]){
LED1=0;
LED2=0;
}else{
LED1=1;
LED2=1;
}
led_ptr%=20;
}
if(pca_int_count){
frame_dog++;
if(frame_dog>=15){//100ms后重新开始分析新的红外线数据包
pca_int_count=0;
frame_dog=0;
}
}
}
}
voidauto_power_down(){
delay(30000);
ISP_CUNTR=0x20;//从AP复位并从AP执行
}
voidmain(void)
{
unsignedchari;
unsignedlongj;
MOTO_IN_A1=0;
MOTO_IN_A2=0;
MOTO_IN_B1=0;
MOTO_IN_B2=0;
P1M1=0xf0; //P1.7~P1.4强推挽输出
EA=0;
power_stat=0;
time0_initialize();
com_initialize(); /*initializeinterruptdrivenserialI/O*/
com_baudrate(4800);/*setupfor1200baud*/
/*
CMOD=0x01; //#00000000B,PCA空闲计数,PCA计数源=Fosc/12,PCA溢出中断(做一个定时器使用)
CCON=0x00; //PCA中断标志清0,PCA停止计数
CL=0x0;
CH=0x0;
CCAPM1=0x31; //PCA1上升下降沿捕获
*/
CMOD=0x03; /*#00000010B,PCA空闲计数,PCA计数源=fosc/2,PCA溢出中断*/
CCON=0x00; //PCA中断标志清0,PCA停止计数
CL=0x0;
CH=0x0;
CCAPM1=0x31; //PCA1上升下降沿捕获
CCAPM0=0x42; //PCA0工作模式:
8位pwm
P