飞思卡尔电磁组检测设计
- 格式:pdf
- 大小:617.94 KB
- 文档页数:20
基于飞思卡尔芯片的电磁引导智能车设计飞思卡尔智能车竞赛是由教育部高等自动化专业教学指导分委员会主办的全国大学生智能汽车竞赛。
所使用的车模是一款带有差速器的后轮驱动模型车,由组委会统一提供。
比赛跑道为表面白色,中心有0.1 mm~0.3mm直径的连续漆泡线作为引导线,其中漆泡线通有100ma交流电流。
比赛规则限定了跑道宽度50cm和拐角最小半径50cm。
飞思卡尔智能车竞赛一、硬件设计1.电磁传感器对于电磁组来说,传感器的选择是尤为重要的,最原始的办法用线圈产生磁场的办法去切割跑到上的磁场来检测道路信息,开始因为线圈的缠绕是有要求的,电感的大小也是有要求的,漆泡线的粗细也是有要求的,基于上面的问题,我们实验没有成功。
后来,围绕传感器做了很多的实验,做了两个传感器:一个是用三极管做放大的,另一个是用运放做放大的,但结果用运放成本高,运放要双电源而且一般的放大器频带窄满足不了要求,所以选择用三极管做放大。
在距离导线50mm的上方放置垂直于导线的10mh 电感,为了能够更加准确测量感应电容式的电压,还需要将上述感应电压进一步放大,一般情况下将电压峰峰值放大到1v~5v左右,就可以进行幅度检测,所以需要放大电路具有100倍左右的电压增益(40db)。
最简单的设计,可以只是用一阶共射三极管放大电路就可以满足要求。
2.速度传感器车模的驱动力来源于一个直流电动机,为了能很好地控制车模的速度,我们引入了闭环控制系统,这就需要车体能实时地或者尽可能快地了解到速度变化,从而对驱动的电压电流进行调整,尽可能快地达到设定速度并且稳定在设定速度上。
从往届的参赛队伍经验得知,使用一个增量编码器能很好地解决以上问题,终选择了欧姆龙的180线增量型光电编码器。
这款编码器为2相输出。
在实际的测试中,让单片机每10ms返回一次传感器的值,当车模在1米/秒左右速度时能返回60~70多个脉冲,当大于2.5米能返回170多个脉冲,反复测试反馈准确,稳定。
精品文档电磁组竞赛车模路径检测设计参考方案(竞赛秘书处2010-1,版本 1.0)一、前言第五届全国大学生智能汽车竞赛新增加了电磁组比赛。
竞赛车模需要能够通过自动识别赛道中心线位置处由通有100mA 交变电流的导线所产生的电磁场进行路径检测。
除此之外在赛道的起跑线处还有永磁铁标志起跑线的位置。
具体要求请参阅《第五届智能汽车竞赛细则》技术文档。
本文给出了一种简便的交变磁场的检测方案,目的是使得部分初次参加比赛的队伍能够尽快有一个设计方案,开始制作和调试自己的车模。
本方案通过微型车模实际运行,证明了它的可行性。
微型车模运行录像参见竞赛网站上视频文件。
二、设计原理1、导线周围的电磁场根据麦克斯韦电磁场理论,交变电流会在周围产生交变的电磁场。
智能汽车竞赛使用路径导航的交流电流频率为20kHz,产生的电磁波属于甚低频(VLF)电磁波。
甚低频频率范围处于工频和低频电磁破中间,为3kHz~30kHz,波长为100km~10km。
如下图所示:图1:电流周围的电磁场示意图导线周围的电场和磁场,按照一定规律分布。
通过检测相应的电磁场的强度和方向可以反过来获得距离导线的空间位置,这正是我们进行电磁导航的目的。
由于赛道导航电线和小车尺寸l远远小于电磁波的波长 ,电磁场辐射能量很小(如果天线的长度l远小于电磁波长,在施加交变电压后,电磁波辐射功率正比于天线长度的四次方),所以能够感应到电磁波的能量非常小。
为此,我们将导线周围变化的磁场近似缓变的磁场,按照检测静态磁场的方法获取导线周围的磁场分布,从而进行位置检测。
精品文档由毕奥-萨伐尔定律知:通有稳恒电流I长度为L的直导线周围会产生磁场,距离导线距离为r处P点的磁感应强度为:精品文档图 2 直线电流的磁场⎝1 4 r由此得: B = cos⎝4 r对于无限长直电流来说,上式中⎝1 = 0 ,⎝ 2 = ,则有B = (1)。
图3:无限长导线周围的磁场强度在上面示意图中,感应磁场的分布是以导线为轴的一系列的同心圆。
小车代码源程序RouteTest.c#include <hidef.h> /* common defines and macros */#include <MC9S12XS128.h> /* derivative information */#include "main.h"#define uint unsigned intuint AD0,AD1,AD2,AD3,AD4,AD5,AD6,AD7,AD8,AD9,ADFULL=0; uint A0=0,A1=0,MAXTEMP0,MINTEMP0,MAXTEMP1,MINTEMP1; uint A2=0,A3=0,MAXTEMP2,MINTEMP2,MAXTEMP3,MINTEMP3; uint A4=0,A5=0,MAXTEMP4,MINTEMP4,MAXTEMP5,MINTEMP5; uint A6=0,A7=0,MAXTEMP6,MINTEMP6,MAXTEMP7,MINTEMP7; uint A8=0,A9=0,MAXTEMP8,MINTEMP8,MAXTEMP9,MINTEMP9;void RouteTest(void){while(!ATD0STAT2_CCF0); //判断通道0是否转换完成AD0=ATD0DR0;if(A0==0){MAXTEMP0=AD0;MINTEMP0=AD0;}else{if(MAXTEMP0<AD0) MAXTEMP0=AD0;if(MINTEMP0>AD0) MINTEMP0=AD0;}A0++;if(A0==LENGTH) {MAXTEMP0=MAXTEMP0-MINTEMP0;}while(!ATD0STAT2_CCF1); //判断通道1是否转换完成 AD1=ATD0DR1;if(A1==0){MAXTEMP1=AD1;MINTEMP1=AD1;}else{if(MAXTEMP1<AD1) MAXTEMP1=AD1;if(MINTEMP1>AD1) MINTEMP1=AD1;}A1++;if(A1==LENGTH) {A1=0;MAXTEMP1=MAXTEMP1-MINTEMP1;}while(!ATD0STAT2_CCF2); //判断通道2是否转换完成 AD2=ATD0DR2;if(A2==0){MAXTEMP2=AD2;MINTEMP2=AD2;}else{if(MAXTEMP2<AD2) MAXTEMP2=AD2;if(MINTEMP2>AD2) MINTEMP2=AD2;}if(A2==LENGTH) {A2=0;MAXTEMP2=MAXTEMP2-MINTEMP2;}while(!ATD0STAT2_CCF3); //判断通道3是否转换完成 AD3=ATD0DR3;if(A3==0){MAXTEMP3=AD3;MINTEMP3=AD3;}else{if(MAXTEMP3<AD3) MAXTEMP3=AD3;if(MINTEMP3>AD3) MINTEMP3=AD3;}A3++;if(A3==LENGTH) {A3=0;MAXTEMP3=MAXTEMP3-MINTEMP3;}while(!ATD0STAT2_CCF4); //判断通道4是否转换完成 AD4=ATD0DR4;if(A4==0){MAXTEMP4=AD4;MINTEMP4=AD4;}else{if(MAXTEMP4<AD4) MAXTEMP4=AD4;if(MINTEMP4>AD4) MINTEMP4=AD4;}A4++;if(A4==LENGTH) {A4=0;MAXTEMP4=MAXTEMP4-MINTEMP4;}while(!ATD0STAT2_CCF5); //判断通道5是否转换完成 AD5=ATD0DR5;if(A5==0){MAXTEMP5=AD5;MINTEMP5=AD5;}else{if(MAXTEMP5<AD5) MAXTEMP5=AD5;if(MINTEMP5>AD5) MINTEMP5=AD5;}A5++;if(A5==LENGTH) {A5=0;MAXTEMP5=MAXTEMP5-MINTEMP5;}while(!ATD0STAT2_CCF6); //判断通道6是否转换完成 AD6=ATD0DR6;if(A6==0){MAXTEMP6=AD6;}else{if(MAXTEMP6<AD6) MAXTEMP6=AD6;if(MINTEMP6>AD6) MINTEMP6=AD6;}A6++;if(A6==LENGTH) {A6=0;MAXTEMP6=MAXTEMP6-MINTEMP6;}while(!ATD0STAT2_CCF7); //判断通道7是否转换完成 AD7=ATD0DR7;if(A7==0){MAXTEMP7=AD7;MINTEMP7=AD7;}else{if(MAXTEMP7<AD7) MAXTEMP7=AD7;if(MINTEMP7>AD7) MINTEMP7=AD7;}A7++;if(A7==LENGTH) {A7=0;MAXTEMP7=MAXTEMP7-MINTEMP7;}while(!ATD0STAT2_CCF8); //判断通道8是否转换完成if(A8==0){MAXTEMP8=AD8;MINTEMP8=AD8;}else{if(MAXTEMP8<AD8) MAXTEMP8=AD8;if(MINTEMP8>AD8) MINTEMP8=AD8;}A8++;if(A8==LENGTH) {A8=0;MAXTEMP8=MAXTEMP8-MINTEMP8;}while(!ATD0STAT2_CCF9); //判断通道9是否转换完成 AD9=ATD0DR9;if(A9==0){MAXTEMP9=AD9;MINTEMP9=AD9;}else{if(MAXTEMP9<AD9) MAXTEMP9=AD9;if(MINTEMP9>AD9) MINTEMP9=AD9;}A9++;if(A9==LENGTH) {A9=0;MAXTEMP9=MAXTEMP9-MINTEMP9;}ADFULL=ADFULL+1;}CarControl.c#include <hidef.h> /* common defines and macros */ #include <MC9S12XS128.h> /* derivative information */ #include "SetPwm.h"#include "main.h"#include "RouteTest.h"#define uint unsigned int#define uchar unsigned char#define value01L -43#define value23L -94#define value45L -90#define value67L -120#define value89L -60#define value01R 43#define value23R 90#define value45R 110#define value67R 130#define value89R 60//#define bentspeed 45//#define dirspeed 45#define valueDL -220#define valueDR 220uint SPEED;//小车速度int CARREL01=0,CARREL23=0,CARREL45=0,CARREL67=0,CARREL89=0; //小车偏移量int ERROR=4050,D_ERROR=0,LASTERROR=4050,E_ERROR=4050,ERRORREL=0; int speedrel=0;uint setspeed=60,realspeed=0;void Delay10us(uint m) //延时10us{uint u;for(;m>0;m--)for(u=0;u<38;u++);}void CarControl(void){//采样100个数据if(ADFULL==LENGTH) {ADFULL=0;//***********************************************CARREL01=MAXTEMP0-MAXTEMP1;CARREL23=MAXTEMP2-MAXTEMP3;CARREL45=MAXTEMP4-MAXTEMP5;CARREL67=MAXTEMP6-MAXTEMP7;CARREL89=MAXTEMP8-MAXTEMP9;if(CARREL01>value01R)//01右转处理{ERROR=4050+CARREL01-value01R;if(ERROR>=4100)ERROR=4100;setspeed=dirspeed;}if(CARREL23>value23R)//23右转处理{ERROR=4100+2*(CARREL23-value23R);if(ERROR>=4264)ERROR=4264;setspeed=dirspeed;}if(CARREL45>value45R)//45右转处理{ERROR=4264+6*(CARREL45-value45R);if(ERROR>=4411)ERROR=4411;setspeed=40;}if(CARREL67>value67R)//67右转处理{ERROR=4411+6*(CARREL67-value67R);if(ERROR>=4600)ERROR=4600;setspeed=bentspeed;}//以上是右转弯处理//******************************************************************* ******//以下是左转弯处理if(CARREL01<value01L)//01{ERROR=4050+CARREL01-value01L;if(ERROR<=4000)ERROR=4000;setspeed=dirspeed;}if(CARREL23<value23L)//23{ERROR=4000+3*(CARREL23-value23L);if(ERROR<=3886)ERROR=3886;setspeed=dirspeed;}if(CARREL45<value45L)//45{ERROR=3886+4*(CARREL45-value45L);if(ERROR<=3794)ERROR=3794;setspeed=(dirspeed+bentspeed)/2;}if(CARREL67<value67L){ERROR=3794+8*(CARREL67-value67L);if(ERROR<=3600)ERROR=3600;setspeed=bentspeed;}D_ERROR=D_ERROR+ERROR-LASTERROR; //误差累积计算 if(D_ERROR>valueDR || D_ERROR<valueDL ) {ERRORREL=D_ERROR;}LASTERROR=ERROR; //保存前一次误差E_ERROR=ERROR+ERRORREL; //叠加误差累计值if(E_ERROR>4600) E_ERROR=4600;if(E_ERROR<3600) E_ERROR=3600;PWMDTY23=E_ERROR;ERRORREL=0;//PWMDTY01=bentspeed;//**************速度控制*************************realspeed=(xishu+1)*speed;speedrel=setspeed-realspeed;if(speedflag==0){if(speedrel<=-10 && (E_ERROR>4400 ||E_ERROR<3800)){PWMDTY45=90; //反转迅速减速PWMDTY01=0;}else{PWMDTY45=0;PWMDTY01=setspeed;}}else{PWMDTY01=setspeed;PWMDTY45=0;}}}Main.c#include <hidef.h> /* common defines and macros */#include <MC9S12XS128.h> /* derivative information */#include "RouteTest.h"#include "CarControl.h"#include "SetPwm.h"#define uint unsigned int#define uchar unsigned char//#define dirspeed 60uint STOPCAR=0,speed,speedsum=0,xishu=0,flag=0,jishi=0; uint bentspeed=0,dirspeed=0;uint speedflag=0;void Delay10(uint m) //延时10us{uint u;for(;m>0;m--)for(u=0;u<38;u++);}void Delay(int k) //延时k*1ms{int u;for(;k>0;k--)for(u=0;u<3998;u++);}//总线时钟设置void setbusclock(void){SYNR = 0x02;REFDV = 0x01;while (!(CRGFLG&0x08));CLKSEL =0x80;}/*****************************************************功能:时基中断初始化,实现5ms中断500us进行一次测速。
飞思卡尔智能车电磁组分区算法介绍写在之前的话:1、⽬前我是⼀名在校学⽣,这也是我第⼀次写博客,不周之处,请多谅解;2、此算法并⾮原创,借鉴⾃⼭东德州学院第⼋届⽩杨队(PS:个⼈看法,对于⼀些⼈把别⼈的开源东西改头换⾯⼀下就说是⾃⼰的原创⾏为⼗分鄙视);3、对于此算法的理解和说明并⾮纸上谈兵,算法已经被我运⽤到了⼩车⽐赛中并取得好的成绩(具体就不多说了,⽐赛时车莫名其妙坏了,⽐赛前调试的速度绝对能进国赛,⽐较遗憾),总之这算法是我尝试过的最好的算法;4、这⼀次所介绍的只是路径算法和⼀些知识普及,后⾯有时间会介绍其余部分算法及许多好的思路(舵机电机控制思路(不只是简单的PID),双车策略);5、希望对于这⽅⾯有涉及的⼈能与我联系并交流或指出不⾜之处。
---------------------------------------------------------------分割线-----------------------------------------------------------------------------⼀、没有这⽅⾯了解的可以看看 飞思卡尔智能车分为三组:摄像头、光电、电磁,我做的是电磁车,三种车队区别在于传感器的不同,所以获得路径信息的⽅法也不⼀样,摄像头和光电识别的是赛道上的⿊线(⽩底赛道),⽽电磁车则是检测埋在赛道下的通⼊100mh电流的漆包线,摄像头和光电采⽤的是摄像头和ccd作为传感器,电磁则是⽤电感放在漆包线周围,则电感上就会产⽣感应电动势,且感应电动势的⼤⼩于通过线圈回路的磁通量成正⽐,⼜因为漆包线周围的磁感应强度不同,因此不同位置的电感的感应电动势就不同,因此就可以去确定电感位置;因此在车⼦前⾯设置了50cm的前瞻,电感布局如下(怎么发不了图⽚):分为两排,前排3个,编号0,1,2(前期还加了两个竖直电感⽤来帮助过直⾓弯,后来改为了⼋字电感);后排2个,编号3,4;现在车⼦获得了不同位置的感应电动势的⼤⼩了,但这些值是不能处理的:1、感应电动势太微弱;2、是模拟信号,信号太微弱就放⼤它;这就涉及到模拟电路的知识了,就不多说了(因为要把这讲完到PCB绘制的篇幅就⾜够写另开⼀号专门写这些⽅⾯来(PS:题外话(我的题外话⽐较多)):放⼤部分外围你设计的再好也抵不过⼀个更好的芯⽚,有两个例⼦,⼀个是我⾃⼰的:之前⽤的是NE5532,但是效果不理想,加了好多什么滤波,补偿,都⽤上,没⽤,软件⾥处理后⾯再说,后来⼀狠⼼换了AD620,感觉像是春天来了,因为它是仪⽤放⼤器,还有就是贵。
第五届飞思卡尔智能车电磁组获奖程序MC9S12XS128单片机、用前置线圈检测磁感线、用无线蓝牙采集数据、干簧管检测起跑线磁铁。
#include <hidef.h> /* common defines and macros */#include "derivative.h" /* derivative-specific definitions */#include <stdio.h>/****************************************************************************** ******一·全局变量声明模块******************************************************************************* ******/typedef unsigned char INT8U;typedef unsigned int INT16U;typedef int INT32;typedef struct {INT8U d; //存放这一次AD转换的值}DATA;/****************************************************全局变量声明区*****************************************************/DA TA data[6]={0}; //全局变量数组,存放赛道AD转换最终结果INT8U a[6][8]={0}; //全局变量用来存放赛道AD转换中间结果INT8U cross0,cross1; //记录十字叉线#define LED PORTA_PA7#define LED_CS PORTA_PA0byte START ;INT16U dianji0;//用来存放上次电机转速PWM,来判断是否减速#define duojmax 9200 //向左转向最大值#define duojmid 8400 //打在中间#define duojmin 7600 //向右转向最小值#define duojcs 8000;#define dianjmax 1200#define dianjmin 10#define dianjmid 600static INT8U look=0,look1=0;int road_change[100]={0}; //判断赛道情况数组int roat_change0;int *r_change0; //指向数组最后一位int *r_change1; //指向数组倒数第二位int sum_front=0,sum_back=0; //分别存储数组前后两部分的和INT16U waittime=0;INT8U choise; //读拨码开关数值/******************************速度测量参数定时********************************/#define PIT0TIME 800 //定时0初值:设定为4MS 测一次速度,采一次AD值#define PIT1TIME 1390 //定时1初值:设定为7ms定时基值/*******************************脉冲记数变量*******************************/ static INT16U PulseCnt;//最终的脉冲数/******************************电机PID变量*********************************/float speed_return_m ;struct {int error0;int error1;int error2;int speed;int chage;float q0,q1,q2,Kp,Kd,Ki;}static SpeedPid;/********************************速度变量设定*******************************/ INT8U speedmax ; //直道加速INT8U speedmin ; //急转弯刹车INT8U speedmid ; //弯道内部限速INT8U speedaveg ; //INT8U breaktime ; //刹车时间////////////////////////////////////////////////////////////////////////////#define speederror_min 2 //允许的最小误差static int NowSpeed;static int speed_control; //存储pid输出值static int speed_return;/*******************************舵机PID参数******************************/struct{int error0;int error1;int error2;int chage;float Kp,Kd,Ki;}PositionPid;int change;static INT16U angle_left [52]={8550,8562,8574,8586,8598,8610,8622,8634,8646,8658,8670,8682,8694,8706,8718,8730,8 742,8754,8766,8778,8790,8802,8814,8826,8838,8850,8862,8874,8886,8898,8910,8922,8934,894 6,8958,8970,8982,8994,9006,9018,9030,9042,9054,9066,9078,9090,9102,9114,9126,9138,9150,9 150};static INT16U angle_right[52]={8250,8238,8226,8214,8202,8190,8178,8166,8154,8142,8130,8118,8106,8094,8 082,8070,8058,8046,8034,8022,8010,7998,7986,7974,7962,7950,7938,7926,7914,7902,7890,787 8,7866,7854,7842,7830,7818,7806,7794,7782,7770,7758,7746,7734,7722,7710,7698,7686,7674,7 662,7650,7650};static INT16U *angle_l=angle_left ,*angle_r=angle_right;static INT16U angle_control=duojmid; //舵机PWM最终控制量static INT16U angle_control0=duojmid;static INT16U angle_control1=duojmid;static INT16U break_pwm=0;INT16U angle_return;/****************************lcd液晶显示变量定义**************************/#define LCD_DATA PORTB#define LCD_RS PORTA_PA4 //PA6#define LCD_RW PORTA_PA5 //PA7#define LCD_E PORTA_PA6 //PA7INT8U start[]={"WELCOME TO LZJTU"};INT8U date[]={"2011-3-15 TUS"};INT8U time[]={"00:00:00"};INT16U Counter=0;INT8U Counter0=0,select=0,min=0;INT8U Counter1=0;INT8U LCD_choice;/**************************标志变量区*************************************/INT8U stop_flag=0;INT8U start_flag=0;INT8U backflag=0;INT8U AD_start ;INT8U zhijwan=0 ;INT8U shizi=0;/****************************************************************************** ******二·初始化函数模块******************************************************************************* ******//**************************************************************1. 芯片初始化--------MCUInit()**************************************************************/void MCUInit(void){//////////////////////////////////////////////////////////////////////////////////////////// ********总线周期计算方法******** //// fBUS=fPLL/2 //// fvoc=2*foscclk*(synr+1)/(refdv+1) //// PLL=2*16M*(219+1)/(69+1)=96Mhz /////////////////////////////////////////////////////////////////////////////////////////////////CLKSEL=0X00;PLLCTL_PLLON=1; //锁相环控制SYNR = 0X40|0X05;REFDV =0X80|0X01;POSTDIV=0X00;while( CRGFLG_LOCK != 1); //等待锁相环时钟稳定,稳定后系统总线频率为24MHz CLKSEL_PLLSEL = 0x01; //选定锁相环时钟PLLCTL=0xf1; //锁相环控制//时钟合成fpllclk=2*foscclk*(synr+1)/(refdv+1)//synr=2;refdv=1;外部时钟foscclk=16mb//fpllclk=48mb 总线时钟24mb// CRGFLG=0x40; //时钟复位控制// CRGINT=0x00 ; //时钟复位中断使能// CLKSEL =0xc0; //时钟选择//COPCTL =0x00;// ARMCOP =0x00; //看门狗复位// RTICTL =0x00; //实时中断}/**************************************************************2. AD转换初始化--------ADCInit()**************************************************************/void ADCInit(void){A TD0CTL1=0x00;A TD0CTL2=0x40; //0100,0000,自动清除使能控制位,忽略外部触发//转换结束允许中断,中断禁止A TD0CTL3=0xA4; //0100,0100,转换序列长度为4;FIFO模式,冻结模式下继续转换A TD0CTL4=0x05; //00001000,8位精度,PRS=5,ATDCLOCK=BusClock(24mb)/(5+1)*2,约为2MHz,采样周期位4倍AD周期A TD0DIEN=0x00; //输入使能禁止}/**************************************************************3. PWM初始化--------PWMInit()**************************************************************/void PWMInit(void) //PWM初始化{//总线频率24mb//1. 选择时钟:PWMPRCLK,PWMSCLA,PWMSCLB,PWMCLKPWME=0x00; //PWM通道关闭PWMPRCLK=0x01; //00010011时钟源A=BusClockA/2=48M/2=24MB;//低位clockA:01,45;高位clockB:23,67 时钟源B=48/1=48MBPWMSCLA =2; //ClockSA=ClockA/2/2=24MB/4=6MBPWMSCLB =2; //ClockSB=ClockB/2/2=12MBHzPWMCLK =0xFF; //通道均级联,均用SA,SB ,且都为6MB//2. 选择极性:PWMPOLPWMPOL =0xff; //电机正反转寄存器(PWMPOL)起始输出为高电平//3. 选择对齐方式:PWMCAEPWMCAE=0x00; //输出左对齐//4.PWMCTL PWM控制寄存器PWMCTL=0xF0; //01,23,45,67通道都级连,输出风别由1,3,5,7口控制//5. 使能PWM通道; PWME//6. 对占空比和周期编程//周期计算公式:输出周期=通道时钟周期*(PWMPERX+1)//占空比:=(PWMPERYX+1)/(PWMPERX+1)//开始时刻应使舵机打直,电机不转//1.通道45用来控制舵机PWMPWMPER45=60000-1; //PWM01=6MB/(60000)=100HzPWME_PWME5 =0; //舵机PWM通道开//2.通道23用来控制电机PWM1,通道01用来作为电机PWM2PWMPER23=1200-1;//电机正转PWM周期初始化。
第七届全国大学生“飞思卡尔”杯智能汽车竞赛电磁组直立行车参考设计方案(版本2.0)目 录目录 (2)图表索引 (3)一、前言 (7)二、原理篇 (9)2.1直立行走任务分解 (9)2.2车模直立控制 (11)2.3 车模角度和角速度测量 (19)2.3车模速度控制 (26)2.4车模方向控制 (33)2.6车模直立行走控制算法总图 (36)三、电路设计篇 (37)3.1整体电路框图 (37)3.2 DSC介绍与单片机最小系统 (39)3.3倾角传感器电路 (42)3.4电机驱动电路 (44)3.5速度传感器电路 (45)3.6电磁线检测电路 (46)3.7 角度计算电路 (50)3.8 车模控制电路全图 (55)四、机械设计篇 (57)4.1车模简化改装 (57)4.2传感器安装 (59)4.3注意事项 (63)五、软件开发篇 (64)5.1软件功能与框架 (65)5.2 DSC的硬件资源配置 (68)5.3主要算法及其实现 (69)六、车模调试篇 (82)6.1 调试参数 (82)6.2调试条件 (85)6.3 桌面静态参数调试 (91)6.4 现场动态参数调试 (101)6.5 方案改进与车模整体水平提高 (101)七、结束语 (102)附录: (103)图表索引第一章图1- 1 电磁组车模直立运行模式 (7)图1- 2参考设计方案内容 (8)图1- 3 车模制作路线图 (9)第二章图2- 1 车模控制任务分解 (10)图2- 2 车模倾角会引起车速速度变化 (10)图2- 3 三层控制之间相互配合 (11)图2- 4 保持木棒直立的反馈控制 (12)图2- 5 通过车轮运动保持车模直立 (12)图2- 6 车模简化成倒立的单摆 (13)图2- 7 普通单摆受力分析 (13)图2- 8 不同阻尼力下的单摆运动 (14)图2- 9 在车轮上的参照系中车模受力分析 (14)图2- 10 车模控制两个系数作用 (16)图2- 11 车模运动方程 (16)图2- 12 加入比例微分反馈后的系统框图 (17)图2- 13 电机在不同电压下的速度变化曲线 (18)图2- 14 加速度传感器原理 (19)图2- 15 MMA7260三轴加速度传感器 (20)图2- 16 车模运动引起加速度信号波动 (21)图2- 17 实际测量MMA7260Z轴信号 (21)图2- 18 车模运动引起加速度Z轴信号变化 (22)图2- 19角速度传感器及参考放大电路 (22)图2- 20 角速度积分得到角度 (23)图2- 21 角速度积分漂移现象 (23)图2- 22 通过重力加速度来矫正陀螺仪的角度漂移 (24)图2- 23 双加速度传感器获得车模角加速度 (25)图2- 24 角度控制框图 (25)图2- 25 电机速度检测 (26)图2- 26 车模倾角给定 (27)图2- 27 车模倾角控制速度中的正反馈 (28)图2- 28 车模倾角控制分析 (29)图2- 29 车模运动速度控制简化模型 (29)图2- 30 增加微分控制后的系统 (30)图2- 31 改进的微分控制 (30)图2- 32 车模角度和速度控制框图 (31)图2- 33 速度角度控制方案的改进 (32)图2- 34 改进后的速度和角度控制方案 (32)图2- 35 检测道路中心电磁线方式 (33)图2- 36 通过电机驱动电压的差动控制控制车模方向 (34)图2- 37 检测车模转动速度的陀螺仪 (34)图2- 38 电感线圈的偏角影响感应电动势 (35)图2- 39 车模方向控制算法 (35)图2- 40 车模运动控制总框图 (36)第三章图3- 1 直立车模控制电路整体框图 (39)图3- 2 56F8013内部资源示意图 (40)图3- 3 F8013最小系统电路 (41)图3- 4 F8013最小系统电路实物 (42)图3- 5 陀螺仪、加速度传感器电路 (43)图3- 6 车模倾角传感器电路实物图 (43)图3- 7 双电机驱动电路 (44)图3- 8单极性PWM、双极性PWM (45)图3- 9 两片33886组成的电机驱动电路 (45)图3- 10 速度传感器电路 (46)图3- 11 基于三极管的电磁信号放大检波电路 (47)图3- 12 基于三极管的电磁放大检波电路实物图 (48)图3- 13 使用R-R运放进行电磁信号放大检波 (49)图3- 14 LMV358放大检波输出波形 (49)图3- 15 基于LMV358放大检波电路实物图 (50)图3- 16 双加速度测量角速度电路 (51)图3- 17 双加速度计测量角度波形图 (51)图3- 18 简化角速度电路 (52)图3- 19 实测车模角速度信号波形 (52)图3- 20 角度信号处理电路 (53)图3- 21 不同角速度比例情况下输出波形 (53)图3- 22 角度计算环节的传递函数 (54)图3- 23 一个运算放大器实现角度计算 (54)图3- 24 不同P1阻值对应的输出波形 (55)图3- 25 简化的角度和角速度处理电路 (55)图3- 26 车模控制电路全图 (56)第四章图4- 1 完整的C型车模底盘 (57)图4- 2 简化后的C型车模底盘 (57)图4- 3 使用热熔胶固定电机支架与车模底盘 (58)图4- 4 去掉后轮之后的车模底盘 (58)图4- 5 电机引线转接板 (59)图4- 6 使用复合胶水固定光电编码盘 (59)图4- 7 固定好的光电码盘和光电检测管 (60)图4- 8 电磁传感器支架 (61)图4- 9 车模组装全图 (64)第五章图5- 1 主程序框架 (65)图5- 2 中断服务程序 (66)图5- 3 任务中断时间波形 (67)图5- 4 算法框图中与控制相关的软件函数 (70)图5- 5 控制函数调用与参数传递关系 (71)图5- 6 程序中变量命名规范 (72)图5- 7 电机死区补偿 (78)第六章图6- 1 调试车模参数复杂而关键 (82)图6- 2 需要调整的参数和相关的单位 (84)图6- 3 车模运动坐标定义 (85)图6- 4 电源检查 (86)图6- 5 单片机串口通信 (86)图6- 6 PWM信号输出 (87)图6- 7 采集电机光电码盘信号 (87)图6- 8 陀螺仪、加速度传感器AD采集信号 (88)图6- 9 车模静态参数调整桌面 (88)图6- 10车模动态参数调试场地 (89)图6- 11 监控软件界面 (89)图6- 12 无线遥控开关 (90)图6- 13 无线通信模块进行参数监控 (90)图6- 14 F8013内部FLASH应用划分 (91)图6- 15 需要整定的传感器参数 (91)图6- 16 车模保持垂直静止 (92)图6- 17 测量加速度传感器的极值 (92)图6- 18测量陀螺传感器比例因子,角度补偿回路断开 (93)图6- 19 几种不同陀螺仪比例因子角度输出 (94)图6- 20 车模控制参数 (95)图6- 21 角度参数调整过程 (96)图6- 22 速度参数调整过程 (97)图6- 23 方向参数调整过程 (98)图6- 24 角度补偿时间常数调整 (99)图6- 25 Z轴附加信号分析 (100)图6- 26 死区常数调整 (100)附录图7- 1 参考设计方案视频截图 (103)图7- 2 参数整定与调试指南 (104)图7- 3 软件控制算法全图 (106)图7- 4 参考方案电路全图 (107)第一章、前言为了提高全国大学生智能汽车竞赛创新性和趣味性,激发高校学生参与比赛的兴趣,提高学生的动手能力、创新能力和接受挑战能力,智能汽车竞赛组委会将电磁组比赛规定为车模直立行走,如图1- 1所示。