找回密码
 立即注册

QQ登录

只需一步,快速开始

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

WiFi智能小车程序

[复制链接]
跳转到指定楼层
楼主
ID:928335 发表于 2021-5-29 09:39 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
  1. #include<reg52.h>
  2. #include<math.h>
  3. #include<intrins.h>
  4. #define uchar unsigned char
  5. #define uint unsigned int
  6. uchar Buffer =0; // 从串口接收的数据
  7. uint URTAReceivedCount=0,n=1;
  8. uchar dataTempdatatable[5],CommandDatatable[5];// 数据包
  9. uchar serVal[2];
  10. uintpwm[]={1120,1190,1382,1382,1382,1382,1382,1382}; // 初始 90 度 , (实际是 1382.4 ,取整得 1382 )
  11. uchar pwm_flag=0;
  12. uint code ms0_5Con=461; //0.5ms 计数   (实际是 460.8 ,取整得 461 )
  13. uint code ms2_5Con=2304; //2.5ms 计数
  14. bit key_stime_ok;
  15. sbit StatusLight=P2^0; // 状态灯
  16. sbit MainLight=P2^1; // 主大灯
  17. sbit servo0=P0^0; // 舵机控制
  18. sbit servo1=P0^1;
  19. sbit servo2=P0^2;
  20. sbit servo3=P0^3;
  21. sbit servo4=P0^4;
  22. sbit servo5=P0^5;
  23. sbit servo6=P0^6;
  24. sbit servo7=P0^7;
  25.    // 定义智能小车驱动模块输入 IO
  26. sbit IN1 = P1^0; //  高电平 1  后退(反转)
  27. sbit IN2 = P1^1; //  高电平 1  前进(正转)
  28. sbit IN3 = P1^2; //  高电平 1  前进(正转)
  29. sbit IN4 = P1^3; //  高电平 1  后退(反转)
  30. sbit EN1 = P1^4; //  高电平使能  
  31. sbit EN2 = P1^5;  //  高电平使能  
  32. /********************************************************************
  33. *  名称  : Delay_1ms()
  34. *  功能  :  延时子程序,延时时间为  1ms * x
  35. *  输入  : x ( 延时一毫秒的个数 )
  36. *  输出  :  无
  37. ***********************************************************************/
  38. void Delay_1ms(uint i)//1ms 延时
  39. {
  40. uchar x,j;
  41. for(j=0;j<i;j++)
  42. for(x=0;x<=148;x++);
  43. }
  44. void TurnOnStatusLight()
  45. {
  46. StatusLight=0;
  47. }
  48. /********************************************************************
  49. *  名称  : Send_Data()
  50. *  功能  :  向上位机传送字符
  51. *  输入  :  无
  52. *  输出  :  无
  53. ***********************************************************************/
  54. void Send_Data(uchar type,uchar cmd,uchardat)
  55. {
  56. uchardata Buffer[5];// 构建数据包
  57. uchar*p;
  58. uintSend_Count=0;
  59. p =Buffer;
  60. Buffer[0]=0XFF;
  61. Buffer[1]=type;
  62. Buffer[2]=cmd;
  63. Buffer[3]=dat;
  64. Buffer[4]=0XFF;
  65. while(1)
  66. {
  67. if(*p==0XFF)
  68. {
  69. Send_Count++; //0XFF 标志统计位
  70. }
  71. SBUF= *p; // 发送
  72. while(!TI) // 如果发送完毕,硬件会置位 TI ,等待发送完毕
  73. {
  74. _nop_();
  75. }
  76. p++;
  77. TI =0;
  78. if(Send_Count == 2) // 当统计到两次出现 0XFF ,则认为一个数据包发送完毕,跳出循环
  79. {
  80. TI =0;
  81. break;
  82. }
  83. }
  84. }
  85. /********************************************************************
  86. 协议规定:
  87. 包头   类型位   数据位   数据位   结束位
  88. 0XFF 0X** OX** 0X** 0XFF
  89. 各命令说明:
  90. 类型位   数据位   数据位   功能
  91. 0X00 0X02 0X00  前进
  92. 0X00 0X01 0X00  后退
  93. 0X00 0X03 0X00  左转
  94. 0X00 0X04 0X00  右转
  95. 0X00 0X00 0X00  停止
  96. 0X01 0X01 角度   舵机 1
  97. 0X01 0X02 . 舵机 2
  98. 0X01 0X01 . 舵机 3
  99. 0X01 0X02 . 舵机 4
  100. 0X01 0X01 . 舵机 5
  101. 0X01 0X02 . 舵机 6
  102. 0X01 0X01 . 舵机 7
  103. 0X01 0X02 数据   舵机 8
  104. 0X02 0X01 车灯亮
  105. 0X02 0X02 车灯灭
  106. 0X03  雷达数据   发送雷达数据  
  107. ***********************************************************************/
  108. /********************************************************************
  109. *  名称  : Com_Int()
  110. *  功能  :  串口中断子函数
  111. ***********************************************************************/
  112. void Com_Int(void) interrupt 4
  113. {
  114. uchar temp;
  115. ES=0; // 关串口中断
  116. RI=0; // 软件清除接收中断
  117. temp=SBUF;
  118. if(temp==0XFF &&URTAReceivedCount<3)
  119. {
  120. Tempdatatable[0]==0XFF; // 包头
  121. URTAReceivedCount++;
  122. }
  123. else
  124. {
  125. Tempdatatable[n]=temp;
  126. n++;
  127. if(URTAReceivedCount==0&&n==2)
  128. n=1;
  129. }
  130. if(URTAReceivedCount==2)// 包尾
  131. {
  132. Tempdatatable[0]=0XFF;
  133. Tempdatatable[4]=0XFF;
  134. n=1;
  135. URTAReceivedCount=0; // 组包完毕
  136. temp="";
  137. //Send_Data(Tempdatatable[1],Tempdatatable[2],Tempdatatable[3]); // 发送组成的数据包回去
  138. }
  139. CommandDatatable[0]=Tempdatatable[0];
  140. CommandDatatable[1]=Tempdatatable[1];
  141. CommandDatatable[2]=Tempdatatable[2];
  142. CommandDatatable[3]=Tempdatatable[3];
  143. CommandDatatable[4]=Tempdatatable[4];
  144. ES=1;// 开串口中断

  145. }
  146. /********************************************************************
  147. *  名称  : Com_Init()
  148. *  功能  :  串口初始化,晶振 11.0592, 波特率 9600 ,使能了串口中断
  149. ***********************************************************************/
  150. void Com_Init(void)
  151. {
  152. TMOD= 0x21;
  153. PCON= 0x00;
  154. SCON= 0x50;
  155. TH1 =0xFd; // 设置波特率  9600
  156. TL1 =0xFd;
  157. TR1 =1; // 启动定时器 1
  158. ES =1; // 开串口中断
  159. EA =1; // 开总中断  
  160. IT0=0;
  161. EX0=1;
  162. }
  163. /********************************************************************
  164. *  名称  :Moto_Forward()
  165. *  功能  :  电机 1 、 2 启动,都是前进,整车表现为前进。
  166. ***********************************************************************/
  167. void Moto_Forward()
  168. {
  169. IN1=0;   // 左电机
  170. IN2=1;
  171. IN3=1;    // 右电机
  172. IN4=0;
  173. EN1=1;
  174. EN2=1;
  175. Delay_1ms(100);
  176. }
  177. /********************************************************************
  178. *  名称  :Moto_Backward()
  179. *  功能  :  电机 1 、 2 启动,都是后退,整车表现为后退。
  180. ***********************************************************************/
  181. void Moto_Backward()
  182. {

  183. IN1=1;   // 左电机
  184. IN2=0;
  185. IN3=0;   // 右电机
  186. IN4=1;
  187. EN1=1;
  188. EN2=1;
  189. Delay_1ms(100);
  190. }
  191. /********************************************************************
  192. *  名称  :Moto_TurnLeft()
  193. *  功能  :  电机 1 后退,电机 2 前进,整车表现为左转。
  194. ***********************************************************************/
  195. void Moto_TurnLeft()
  196. {
  197. IN1=0;   // 左电机
  198. IN2=0;
  199. IN3=1;   // 右电机
  200. IN4=0;
  201. EN1=1;
  202. EN2=1;
  203. Delay_1ms(100);
  204. }
  205. /********************************************************************
  206. *  名称  :Moto_TurnRight()
  207. *  功能  :  电机 1 前进,电机 2 后退,整车表现为右转。
  208. ***********************************************************************/
  209. void Moto_TurnRight()
  210. {
  211. IN1=0;   // 左电机
  212. IN2=1;
  213. IN3=0;   // 右电机
  214. IN4=0;
  215. EN1=1;
  216. EN2=1;
  217. Delay_1ms(100);
  218. }
  219. /********************************************************************
  220. *  名称  :Moto_Stop()
  221. *  功能  :  电机 1 停止,电机 2 停止,整车表现为停止。
  222. ***********************************************************************/
  223. void Moto_Stop()
  224. {

  225. IN1=0;   // 左电机
  226. IN2=0;
  227. IN3=0;   // 右电机
  228. IN4=0;
  229. EN1=1;
  230. EN2=1;
  231. Delay_1ms(100);
  232. }
  233. /********************************************************************
  234. *  功能  :  舵机 PWM 中断初始化
  235. ***********************************************************************/
  236. void Timer0Init()
  237. {
  238. /*0 度 =0.5ms, 45 度 =1ms, 90 度 =1.5ms, 135 度 =2ms, 180 度 =2.5ms
  239. /.5ms 初始值  F700, (12n/11059200=2.5/1000,n=2304, X=65536-2304=63232 > F700)*/
  240. TMOD|= 0x01;  // 使用模式 1 , 16 位定时器,使用 "|" 符号可以在使用多个定时器时不受影响   
  241. TH0=-ms2_5Con>>8;  // 给定初值, 17ms 中断
  242. TL0=-ms2_5Con;
  243. EA=1;// 总中断打开
  244. ET0=1; // 定时器 0 中断打开
  245. TR0=1; // 定时器 0 开关打开  
  246. }
  247. /********************************************************************
  248. *  功能  :  舵机 PWM 中断 , // 舵机控制函数   周期为 20ms  一个循环 20MS = 8*2.5ms
  249. ***********************************************************************/
  250. void SteeringGear() interrupt 1
  251. {
  252. switch(pwm_flag)
  253. {
  254. case1: servo0=1; TH0=-pwm[0]>>8; TL0=-pwm[0]; break;
  255. case2: servo0=0; TH0=-(ms2_5Con-pwm[0])>>8; TL0=-(ms2_5Con-pwm[0]); break;
  256. case3: servo1=1; TH0=-pwm[1]>>8; TL0=-pwm[1]; break;
  257. case4: servo1=0; TH0=-(ms2_5Con-pwm[1])>>8; TL0=-(ms2_5Con-pwm[1]); break;
  258. case5: servo2=1; TH0=-pwm[2]>>8; TL0=-pwm[2]; break;
  259. case6: servo2=0; TH0=-(ms2_5Con-pwm[2])>>8; TL0=-(ms2_5Con-pwm[2]); break;
  260. case7: servo3=1; TH0=-pwm[3]>>8; TL0=-pwm[3]; break;
  261. case8: servo3=0; TH0=-(ms2_5Con-pwm[3])>>8; TL0=-(ms2_5Con-pwm[3]); break;
  262. case9: servo4=1; TH0=-pwm[4]>>8; TL0=-pwm[4]; break;
  263. case10: servo4=0; TH0=-(ms2_5Con-pwm[4])>>8; TL0=-(ms2_5Con-pwm[4]); break;
  264. case11: servo5=1; TH0=-pwm[5]>>8; TL0=-pwm[5]; break;
  265. case12: servo5=0; TH0=-(ms2_5Con-pwm[5])>>8; TL0=-(ms2_5Con-pwm[5]); break;
  266. case13: servo6=1;TH0=-pwm[6]>>8; TL0=-pwm[6]; break;
  267. case14: servo6=0;TH0=-(ms2_5Con-pwm[6])>>8; TL0=-(ms2_5Con-pwm[6]); break;
  268. case15: servo7=1;TH0=-pwm[7]>>8; TL0=-pwm[7]; break;
  269. case16: servo7=0;TH0=-(ms2_5Con-pwm[7])>>8; TL0=-(ms2_5Con-pwm[7]); break;
  270.   default: TH0=0xff; TL0=0x80; pwm_flag=0;
  271. }
  272. pwm_flag++;
  273. }
  274. voidSetSteeringGear(uchar i, uchar val)
  275. {
  276. uinta = (val+46)*10;
  277. if(a<ms0_5Con)
  278.   a=ms0_5Con;
  279. if(a>ms2_5Con)
  280.   a=ms2_5Con;
  281. pwm[i]=a;
  282. CommandDatatable[2]=0xff; // 清除缓存
  283. }
  284. /********************************************************************
  285. *  功能  :  串口中断接收数据
  286. ***********************************************************************/

  287. /*********************************************************************************
  288. **  函数功能   :   主函数
  289. *********************************************************************************/
  290. void main()
  291. {

  292. MainLight=0;
  293. Delay_1ms(200);
  294. Com_Init();// 串口初始化
  295. Timer0Init();// 舵机 PWM 中断初始化  
  296. while(1)
  297. {

  298. if(CommandDatatable[0]==0XFF &&CommandDatatable[4]==0XFF)
  299. {
  300. switch (CommandDatatable[1]) // 根据键值不同,执行不同的内容
  301. {
  302. case0X00: // 类型位 0X00 ,表明是控制数据包,进入控制数据 case
  303. switch(CommandDatatable[2]) // 根据数据位的值来进行选择执行不同的动作
  304. {
  305. case0X00:Moto_Stop();break;
  306. case0X01:Moto_Forward();break;
  307. case0X02:Moto_Backward();break;
  308. case0X03:Moto_TurnLeft();break;
  309. case0X04:Moto_TurnRight();break;
  310.             default : break;
  311. }
  312. break;
  313. case0X01: // 类型位 0X01 ,表明是舵机数据包,进入舵机 case
  314. switch(CommandDatatable[2])
  315. {
  316. case0x01:SetSteeringGear(0,CommandDatatable[3]);break;
  317.   case 0x02:SetSteeringGear(1,CommandDatatable[3]);break;
  318.   case 0x03:SetSteeringGear(2,CommandDatatable[3]);break;
  319.   case 0x04:SetSteeringGear(3,CommandDatatable[3]);break;
  320.   case 0x05:SetSteeringGear(4,CommandDatatable[3]);break;
  321.   case 0x06:SetSteeringGear(5,CommandDatatable[3]);break;
  322.     case 0x07:SetSteeringGear(6,CommandDatatable[3]);break;
  323.   case 0x08:SetSteeringGear(7,CommandDatatable[3]);break;
  324.         default : break;
  325. }
  326. break;
  327. case0X02: // 类型位 0X02 ,表明是大灯数据包,进入大灯 case
  328. switch(CommandDatatable[2])
  329. {
  330. case0X01:MainLight=1;break;
  331. case0X02:MainLight=0;break;
  332.             default : break;
  333. }
  334. break;
  335. default : break;
  336. }
  337. }
  338. }
  339. }
复制代码


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

使用道具 举报

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

本版积分规则

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

Powered by 单片机教程网

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