找回密码
 立即注册

QQ登录

只需一步,快速开始

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

有人能帮我解释下这个单片机公交车自动报站红外模块的原理吗?

[复制链接]
跳转到指定楼层
楼主
在某一个宝上买的公交车自动报站项目学习资料,问了店家几次也讲不明白。
这个红外线发射电路是单片机编码?
接收电路我知道是用VS1838红外接收头接收的红外信号,然后解码传送给单片机,但红外发射电路(从机)就一个单片机连接一个二极管就完成红外信号的编码和发送。不明白这个红外发射电路的原理

主机程序:
  1. #include <reg52.h>                 //调用单片机头文件
  2. #define uchar unsigned char  //无符号字符型 宏定义        变量范围0~255
  3. #define uint  unsigned int         //无符号整型 宏定义        变量范围0~65535

  4. sbit rs=P2^5;         //寄存器选择信号 H:数据寄存器          L:指令寄存器
  5. sbit rw=P2^6;         //寄存器选择信号 H:数据寄存器          L:指令寄存器
  6. sbit e =P2^7;         //片选信号   下降沿触发

  7. sbit hw_P32=P3^2;                   //红外遥控接的IO口
  8. uchar hw_table[4];           //红外解码的缓冲区
  9. bit flag_jiema_en = 1; //红外解码成功标志

  10. uchar geshu=2;

  11. uchar code gj_ming[]="直达车  ";

  12. uchar code  table1[]="1号站  ";
  13. uchar code  table2[]="  2号站    ";



  14. /***********************语音模块控制IO口的定义************************/
  15. sbit  VRST = P3^7;
  16. sbit  VBUSY= P3^6;        
  17. sbit  VSDA = P3^5;
  18. sbit  VCS  = P3^4;  
  19. sbit  VSCL = P3^3;


  20. /********************************************************************
  21. * 名称 : delay_1ms()
  22. * 功能 : 延时1ms函数
  23. * 输入 : q
  24. * 输出 : 无
  25. ***********************************************************************/
  26. void delay_1ms(uint q)
  27. {
  28.         uint i,j;
  29.         for(i=0;i<q;i++)
  30.                 for(j=0;j<120;j++);
  31. }


  32.                                    
  33.                                           
  34. /************ 延时函数  *****************/
  35. void delay_uint(uint z)
  36. {
  37.    while(z--);
  38. }

  39. /***************交换函数 高位变低位 低位变高位*****************/
  40. uchar change_dat(uchar dat)
  41. {
  42.         uchar i,value;
  43.         for(i=0;i<8;i++)
  44.         {        
  45.                 value <<= 1;
  46.                 if((dat & 0x01) == 0x01)
  47.                         value |= 0x01;
  48.                 dat >>= 1;        
  49.         }
  50.         return value;
  51. }

  52. /************ 写命令函数  *****************/
  53. void write_com(uchar com)
  54. {

  55.    P0=change_dat(com);
  56.    rw=0;
  57.    rs=0;
  58.    delay_uint(25);
  59.    e=1;
  60.    delay_uint(50);
  61.    e=0;
  62. }
  63. /************ 写数据函数  *****************/
  64. void write_dat(uchar dat)
  65. {

  66.    P0=change_dat(dat);
  67.    rw=0;
  68.    rs=1;
  69.    delay_uint(25);
  70.    e=1;
  71.    delay_uint(50);
  72.    e=0;
  73. }

  74. /**********************************************************
  75. *函数名: addr_12864
  76. *功能:写地址
  77. *说明:写汉字时要写个地址
  78. *输入:无
  79. *返回:无
  80. **********************************************************/
  81. void addr_12864(uchar hang,uchar lie)          //地址转换
  82. {
  83.         uchar address;
  84.         switch(hang)
  85.         {
  86.                 case 1: address=0x80 + lie ;
  87.                                 break;
  88.                 case 2: address=0x90 + lie ;
  89.                                 break;
  90.                 case 3: address=0x88 + lie ;
  91.                                 break;
  92.                 case 4: address=0x98 + lie ;
  93.                                 break;
  94.                 default :
  95.                                 break;
  96.         }        
  97.         write_com(address);
  98. }

  99. /**********************************************************
  100. *函数名: write_string
  101. *功能:在12864上显示字符数据
  102. *说明:
  103. *输入:无
  104. *返回:无
  105. **********************************************************/

  106. void write_string(uchar hang,uchar lie,uchar *p)
  107. {
  108.         addr_12864(hang,lie);          //地址转换
  109.         while(*p != '\0')
  110.         {
  111.                 write_dat(*p);
  112.                 p++;
  113.                 delay_uint(50);
  114.         }
  115. }




  116. /************12864液晶初始化函数*****************/
  117. void init_12864()
  118. {
  119.    write_com(0x30);
  120.    write_com(0x0c);
  121.    write_com(0x01);         
  122.    delay_1ms(100);
  123. }

  124. /************初始化显示*****************/
  125. void init_12864_dis()
  126. {
  127.         write_string(1,0,"    欢迎乘坐    ");
  128.         write_string(2,0,gj_ming);
  129.         write_string(3,0,"                ");
  130.         write_string(4,0,"                ");
  131. }


  132. /***********************语音子程序************************/
  133. void Send_threelines(unsigned char addr,uchar dat)
  134. {
  135.    unsigned char i;
  136.         VRST=0;
  137.         VRST=1;
  138.         VCS=0;
  139.     for(i=0;i<8;i++)
  140.         {
  141.                 VSCL=0;
  142.                 if(addr&0x01)
  143.                 {
  144.                         VSDA=1;
  145.                 }
  146.                 else
  147.                         VSDA=0;
  148.                 addr>>=1;
  149.                 VSCL=1;
  150.         }
  151.         VCS=1;
  152.         if(dat == 1)
  153.                 while(VBUSY == 0);          //忙等待
  154. }


  155. /***************100us的延时函数***12M晶振*****************/
  156. void delay_100us(uchar z)
  157. {                                //12M
  158.    uchar x,y;
  159.    for(x=0;x<z;x++)
  160.      for(y=0;y<20;y++);
  161. }


  162. /********************独立按键程序*****************/
  163. uchar key_can;         //按键值

  164. void key()         //独立按键程序
  165. {
  166.         if((P1 & 0x0f) != 0x0f)                //按键按下
  167.         {
  168.                 delay_1ms(1);                     //按键消抖动
  169.                 if((P1 & 0x0f) != 0x0f)
  170.                 {                                                //确认是按键按下
  171.                         switch(P1 & 0x0f)
  172.                         {
  173.                                 case 0x0e: key_can = 2; break;          //得到按键值
  174.                                 case 0x0d: key_can = 1; break;          //得到按键值
  175.                         }
  176.                 }                        
  177.         }
  178. }


  179. /***********外部中断0初始化程序****************/
  180. void init_int0()
  181. {
  182.         EX0=1;                          //允许外部中断0中断
  183.         EA=1;                           //开总中断
  184.         IT0 = 1;                   //外部中断0负跳变中断
  185. }

  186. /***************主函数*****************/
  187. void main()
  188. {         
  189.         uchar num;
  190.         P0 = P1 = P2 = P3 = 0XFF;
  191.         init_12864();                        
  192.         init_12864_dis();
  193.         Send_threelines(0,0);    //语音播报
  194.         init_int0();                                        //外部中断初始化
  195.         while(1)
  196.         {
  197.                 if(flag_jiema_en == 1)                        
  198.                 {
  199.                         flag_jiema_en = 0;
  200.                         if(hw_table[2] == 0x45)
  201.                         {
  202.                                 write_string(1,0,gj_ming);
  203.                                 write_string(2,0,table1);
  204.                                 write_string(3,0,"                ");
  205.                                 write_string(4,0,"                ");
  206.                                 Send_threelines(1,1);    //语音播报        
  207.                         }
  208.                         if(hw_table[2] == 0x47)
  209.                         {
  210.                                 write_string(1,0,gj_ming);
  211.                                 write_string(2,0,table2);
  212.                                 write_string(3,0,"                ");
  213.                                 write_string(4,0,"                ");
  214.                                 Send_threelines(2,1);    //语音播报                        
  215.                         }
  216.                         hw_table[2] = 0;
  217.                 }
  218.                 key();         //独立按键程序        
  219.                 if(key_can == 1)
  220.                 {
  221.                         if(num < 2)
  222.                         {         
  223.                                 num ++;        
  224.                                 if(num == 1)       //报第1个站
  225.                                 {
  226.                                         write_string(1,0,gj_ming);
  227.                                         write_string(2,0,table1);
  228.                                         write_string(3,0,"                ");
  229.                                         write_string(4,0,"                ");
  230.                                         Send_threelines(1,0);    //语音播报        
  231.                                 }
  232.                                 if(num == 2)       //报第2个站
  233.                                 {
  234.                                         write_string(1,0,gj_ming);
  235.                                         write_string(2,0,table2);
  236.                                         write_string(3,0,"                ");
  237.                                         write_string(4,0,"                ");
  238.                                         Send_threelines(2,0);    //语音播报                        
  239.                                 }
  240.                         }
  241.                 }
  242.                 if(key_can == 2)
  243.                 {
  244.                         if(num != 0)
  245.                                 num--;        
  246.                         if(num == 1)       //报第1个站
  247.                         {
  248.                                         write_string(1,0,gj_ming);
  249.                                         write_string(2,0,table1);
  250.                                         write_string(3,0,"                ");
  251.                                         write_string(4,0,"                ");
  252.                                 Send_threelines(1,0);    //语音播报        
  253.                         }
  254.                         if(num == 2)       //报第2个站
  255.                         {
  256.                                         write_string(1,0,gj_ming);
  257.                                         write_string(2,0,table2);
  258.                                         write_string(3,0,"                ");
  259.                                         write_string(4,0,"                ");
  260.                                 Send_threelines(2,0);    //语音播报                        
  261.                         }
  262.                 }
  263.         }
  264. }


  265. /*****************红外解码程序********************/
  266. void int0() interrupt 0
  267. {
  268.         unsigned char i,j;
  269.         delay_100us(20);     //防止干扰
  270.         if(hw_P32 == 0)
  271.         {                                     //引导码
  272.                 while(hw_P32 == 0); //等待低电平过完
  273.                 delay_100us(20);         
  274.                 if(hw_P32 == 1)          //引码结束
  275.                 {         
  276.                         delay_100us(20);  // 说明高电平已经过完 引导码已经结束
  277.                         for(i=0;i<4;i++)
  278.                                 for(j=0;j<8;j++)
  279.                                 {
  280.                                         while(hw_P32 == 0);   //等待过完
  281.                                         delay_100us(5);
  282.                                         if(hw_P32 == 0)                //数据0的时间
  283.                                         {                                        //数据1的时间
  284.                                                 hw_table[i] >>= 1;    //低位在前
  285.                                         }
  286.                                         else
  287.                                         {        
  288.                                                 delay_100us(5);   //   高电平的时间过完
  289.                                                 hw_table[i] >>= 1;    //低位在前
  290.                                                 hw_table[i] |= 0x80;  //数据值1
  291.                                         }
  292.                                 }
  293.                         flag_jiema_en = 1;          //红外解码成功        
  294.                 }
  295.         }
  296. }


  297. 从机程序:
  298. #include"reg52.h"
  299. #define uint unsigned int
  300. #define uchar unsigned char
  301. sbit  P35=P2^7;                                         //  定义控制红外发射管的控制引脚
  302. uchar fa_value;

  303. /***********   延时函数  ***********/
  304. void delay_1ms(uint z)           //  延时  z 毫秒
  305. {
  306.   uint x,y;
  307.   for(x=z;x>0;x--)
  308.     for(y=110;y>0;y--) ;
  309. }
  310. /***************100us的延时函数***12M晶振*****************/
  311. void delay_100us(uchar z)
  312. {                                //12M
  313.    uchar x,y;
  314.    for(x=0;x<z;x++)
  315.      for(y=0;y<20;y++);
  316. }

  317. /***********   红外发射子程序  ***********/
  318. void hongwaifase(uchar dat)                 //  发射dat
  319. {
  320.         uchar i,j,str[4];                         //  str[4]存放等待发射的四个数据
  321.         str[0]=0xff;str[1]=0x00;
  322.         str[2]=dat;str[3]=~dat;
  323.         TR1=1;
  324.         delay_100us(90);                                   //起始信号    9毫秒
  325.         TR1=0;
  326.         delay_100us(45);                                         
  327.         for(j=0;j<4;j++)                           //发射四个数据
  328.         {
  329.                 for(i=0;i<8;i++)                   //  发射八个位
  330.                 {
  331.                         TR1=1;
  332.                         delay_100us(5);                  //  0.56毫秒                        
  333.                         TR1=0;
  334.                         if(str[j]&0x01==0x01)
  335.                                 delay_100us(11);                        //11.2毫秒  代表发送1
  336.                         else
  337.                                 delay_100us(5);                                //0.56毫秒  代表发送0
  338.                         str[j]>>=1;
  339.                 }
  340.         }                 
  341. }
  342. void init()
  343. {
  344.   EA=1;
  345.   ET1=1;
  346.   TR1 = 1;
  347.   TMOD=0X20;
  348.   TH1=0XF0;
  349.   TL1=0XF0;           //  用定时器中断产生38khz的方波
  350. }

  351. void main()
  352. {
  353.         init();
  354.     while(1)
  355.         {                  
  356.                 hongwaifase(0x45);
  357.                 delay_1ms(1000);
  358.         }        
  359. }

  360. void time1() interrupt 3 using 1
  361. {
  362.    P35=~P35;                //取反产生方波
  363. }
复制代码

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

使用道具 举报

沙发
ID:968316 发表于 2021-9-26 11:42 来自手机 | 只看该作者
有没有去问客服呀?
回复

使用道具 举报

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

本版积分规则

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

Powered by 单片机教程网

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