找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1523|回复: 0
打印 上一主题 下一主题
收起左侧

基于51单片机的蓝牙避障小车代码

[复制链接]
跳转到指定楼层
楼主
学习时候自己写的,两驱四驱皆可用

单片机源程序如下:
  1. /******************************************************************************
  2. 2021.9.27
  3. 单片机实践二 孟瑞淞
  4. 超声波舵机避障程序
  5. ******************************************************************************/
  6. #include <AT89x52.H>
  7. #include <intrins.h>
  8. #define led1 {P0_6=1,P0_6=0;}
  9. #define led2 {P0_7=0,P0_7=1;}
  10.        
  11. #define Right_moto_go     {P1_2=1,P1_3=0;}        //右边电机向前走
  12. #define Right_moto_back   {P1_2=0,P1_3=1;}        //右边电机向后走
  13. #define Right_moto_Stop   {P1_2=0,P1_3=0;}        //右边电机停转   

  14. #define Left_moto_go      {P1_6=1,P1_7=0;}  //左边电机向前走
  15. #define Left_moto_back    {P1_6=1,P1_7=0;}         //左边电机向后转
  16. #define Left_moto_Stop    {P1_6=0,P1_7=0;}  //左边电机停转                     
  17.        
  18. #define Sevro_moto_pwm  P2_2      //接舵机信号端输入PWM信号调节速度
  19. #define  ECHO  P2_0                                        //超声波接口定义
  20. #define  TRIG  P2_1                                //超声波接口定义
  21.        

  22. unsigned char const positon[3]={ 0xfe,0xfd,0xfb};
  23. unsigned char disbuff[4]={ 0,0,0,0,};
  24. unsigned char posit=0;

  25. unsigned char pwm_val_left  = 0;//变量定义
  26. unsigned char push_val_left =14;//舵机归中,产生约,1.5MS 信号
  27. unsigned long S=0;
  28. unsigned long S1=0;
  29. unsigned long S2=0;
  30. unsigned long S3=0;
  31. unsigned long S4=0;
  32. unsigned int  time=0;                    //时间变量
  33. unsigned int  timer=0;                        //延时基准变量
  34. unsigned char timer1=0;                        //扫描时间变量                                       
  35.    
  36. /************************************************************************/       
  37. //延时函数       
  38. void delay(unsigned int k)
  39. {                               
  40.                    unsigned int x,y;
  41.                    for(x=0;x<k;x++)
  42.                    for(y=0;y<2000;y++);
  43. }
  44. /************************************************************************/       
  45. //前速前进
  46. void run(void)
  47. {
  48.    
  49.             Left_moto_go;    //左电机往前走
  50.             Right_moto_go ;  //右电机往前走
  51. }

  52. //前速后退
  53. void backrun(void)
  54. {
  55.    
  56.                  Left_moto_back ;   //左电机往前走
  57.                  Right_moto_back ;  //右电机往前走
  58. }

  59. //左转
  60. void  leftrun(void)
  61. {
  62.    
  63.                   Right_moto_go ;  //右电机往前走 ;
  64.                   Left_moto_Stop ;   //左电机停止
  65. }

  66. //右转
  67. void  rightrun(void)
  68. {
  69.    
  70.                    Left_moto_go ;   //左电机往前走
  71.                    Right_moto_Stop ;  //右电机停止
  72. }
  73. //停
  74. void  stoprun(void)
  75. {
  76.    
  77.                   Left_moto_Stop ;   //左电机往前走
  78.                   Right_moto_Stop ;  //右电机往前走
  79. }

  80. void  StartModule()                       //启动测距信号
  81. {
  82.           TRIG=1;                                        
  83.           _nop_();
  84.           _nop_();
  85.           _nop_();
  86.           _nop_();
  87.           _nop_();
  88.           _nop_();
  89.           _nop_();
  90.           _nop_();
  91.           _nop_();
  92.           _nop_();
  93.           _nop_();
  94.           _nop_();
  95.           _nop_();
  96.           _nop_();
  97.           _nop_();
  98.           _nop_();
  99.           _nop_();
  100.           _nop_();
  101.           _nop_();
  102.           _nop_();
  103.           _nop_();
  104.           TRIG=0;
  105. }

  106. void Conut(void)                   //计算距离
  107. {
  108.           while(!ECHO);                       //当RX为零时等待
  109.           TR0=1;                               //开启计数
  110.           while(ECHO);                           //当RX为1计数并等待
  111.           TR0=0;                                   //关闭计数
  112.           time=TH0*256+TL0;                   //读取脉宽长度
  113.           TH0=0;
  114.           TL0=0;
  115.           S=(time*1.7)/100;        //算出来是CM
  116.           disbuff[0]=S%1000/100;   //更新显示
  117.           disbuff[1]=S%1000%100/10;
  118.           disbuff[2]=S%1000%10 %10;
  119. }

  120. void  COMM( void )                      
  121. {
  122.                   push_val_left=5;          //舵机向左转90度
  123.                   timer=0;
  124.                   while(timer<=4000); //延时400MS让舵机转到其位置
  125.                   StartModule();          //启动超声波测距
  126.           Conut();                           //计算距离
  127.                   S2=S;  
  128.   
  129.                   push_val_left=23;          //舵机向右转90度
  130.                   timer=0;
  131.                   while(timer<=4000); //延时400MS让舵机转到其位置
  132.                   StartModule();          //启动超声波测距
  133.           Conut();                          //计算距离
  134.                   S4=S;        
  135.        
  136.                   push_val_left=14;          //舵机归中
  137.                   timer=0;
  138.                   while(timer<=4000); //延时400MS让舵机转到其位置
  139.                   StartModule();          //启动超声波测距
  140.           Conut();                          //计算距离
  141.                   S1=S;        

  142.           if((S2<20)||(S4<20)) //只要左右各有距离小于,20CM小车后退
  143.                   {
  144.                   backrun();                   //后退
  145.                   timer=0;
  146.                   while(timer<=4000);
  147.                   }
  148.                   
  149.                   if(S2>S4)       
  150.                            
  151.                      {
  152.                                     rightrun();          //车的左边比车的右边距离小        右转       
  153.                         timer=0;
  154.                         while(timer<=3500);//原4000
  155.                      }                                     
  156.                        else
  157.                      {
  158.                        leftrun();                //车的左边比车的右边距离大        左转
  159.                        timer=0;
  160.                        while(timer<=3500);//原4000
  161.                      }
  162. }

  163. /*定时器产生100US定时信号*/
  164. void pwm_Servomoto(void)
  165. {  

  166.                    if(pwm_val_left<=push_val_left)
  167.                        Sevro_moto_pwm=1;
  168.                        else
  169.                        Sevro_moto_pwm=0;
  170.                        if(pwm_val_left>=200)
  171.                           pwm_val_left=0;
  172. }

  173. /*TIMER1中断服务子函数产生PWM信号*/
  174. void time1()interrupt 3   using 2
  175. {       
  176.             TH1=(65536-100)/256;          //100US定时
  177.                 TL1=(65536-100)%256;
  178.                 timer++;                                  //定时器100US为准。在这个基础上延时
  179.                 pwm_val_left++;
  180.                 pwm_Servomoto();
  181. }

  182. void delay1()
  183. {
  184.                 unsigned char i,j,k;
  185.                 for(i=1;i>0;i--)
  186.                    for(j=100;j>0;j--)
  187.                 for(k=250;k>0;k--);
  188. }

  189. void shansuo()
  190. {
  191.                      led1;
  192.                      delay1();
  193.                      led2;
  194.                      delay1();                 
  195. }
  196.          
  197. /*--主函数--*/
  198. void main(void)
  199. {
  200.           stoprun();
  201.               TMOD=0X11;
  202.               TH1=(65536-100)/256;          //100US定时
  203.               TL1=(65536-100)%256;
  204.               TH0=0;
  205.                TL0=0;  
  206.               TR1= 1;
  207.               ET1= 1;
  208.               ET0= 1;
  209.               EA = 1;
  210.               delay(100);
  211.           push_val_left=14;          //舵机归中
  212.               while(1)                     
  213.               {
  214.                    shansuo();        //闪烁灯函数
  215.                    if(timer>=200)          //100MS检测启动检测一次 原来500
  216.                    {
  217.                       timer=0;
  218.                           StartModule(); //启动检测
  219.                   Conut();                  //计算距离
  220.                   if(S<35)                  //距离小于20CM
  221.                           {
  222.                              stoprun();          //小车停止
  223.                              COMM();                                  //方向函数
  224.                           }
  225.                           else
  226.                           if(S>40)                  //距离大于,35CM往前走
  227.                           run();
  228.                    }
  229.                }
  230. }
  231.        
复制代码

Keil代码下载:
单片机实践二.rar (364.02 KB, 下载次数: 17)


评分

参与人数 1黑币 +30 收起 理由
admin + 30 共享资料的黑币奖励!

查看全部评分

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏1 分享淘帖 顶 踩
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表