找回密码
 立即注册

QQ登录

只需一步,快速开始

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

单片机+ADC0832热敏电阻检测pm2.5程序及PCB图

[复制链接]
跳转到指定楼层
楼主
热敏电阻测温度程序及PCB
仿真原理图如下(proteus仿真工程文件可到本帖附件中下载)



Altium Designer画的原理图和PCB图如下:(51hei附件中可下载工程文件)



单片机+ADC0832源程序如下:
  1. #include <AT89X52.h>
  2. #include <intrins.h>
  3. #define uint unsigned int
  4. #define uchar unsigned char   
  5. typedef unsigned char unint8;
  6. typedef unsigned char unint16;
  7. sbit RS=P2^5;
  8. sbit RW=P2^6;
  9. sbit EN=P2^7;
  10. sbit  LED1 = P2^0;
  11. sbit  LED = P1^1;
  12. sbit ADCS = P1^4;
  13. sbit ADCLK = P1^0;
  14. sbit ADDI = P1^2;
  15. sbit ADDO = P1^ 2;
  16. sbit SET= P3^3;
  17. sbit ADD= P3^4;
  18. sbit DEC= P3^5;
  19. sbit BEEP=P3^6;
  20. sbit TRH = P1^3;
  21. uchar set_st;
  22. uchar tab[4];
  23. uint DUST_SET=35;
  24. bit shanshuo_st;   
  25. bit beep_st;     
  26. uchar x=4;     
  27. //定义标识
  28. uchar FlagStart = 0;
  29. float   DUST_Value;
  30. uint DUST;
  31. uchar num=0;
  32. uchar mm;
  33. uchar ADC_Get[10]={0};           
  34. uchar str[5]={0};
  35. uchar abc;
  36. unsigned char str1[]={"        "};
  37. unsigned char str2[]={"        "};

  38. unint8 TH_data,TL_data,RH_data,RL_data,CK_data;
  39. unint8 TH_temp,TL_temp,RH_temp,RL_temp,CK_temp;
  40. unint8 com_data,untemp,temp;
  41. unint8 respond;

  42. /*****初始化定时器0*****/
  43. void InitTimer(void)
  44. {
  45.         TMOD = 0x01;      
  46.         TL0 = (65536-10000)/256; //定时10ms   
  47.         TH0 = (65536-10000)%256;   
  48.         TR0 = 1;
  49.         ET0 = 1;   
  50.         EA = 1;
  51. }
  52. /*************************lcd1602程序**************************/
  53. void delay1ms(uint ms)
  54. {  uint i,j;
  55.    for(i=0;i<ms;i++)
  56.     for(j=0;j<100;j++);
  57. }
  58. unsigned char rolmove(unsigned  char m)
  59. {
  60.   
  61.   unsigned char   a,b,c,d,e,f,g,h;               
  62. a=(m&0x01)<<7;
  63. b=(m&0x02)<<5;
  64. c=(m&0x04)<<3;
  65. d=(m&0x08)<<1;
  66. e=(m&0x10)>>1;
  67. f=(m&0x20)>>3;
  68. g=(m&0x40)>>5;
  69. h=(m&0x80)>>7;
  70. m=a|b|c|d|e|f|g|h;
  71. return m;
  72. }
  73. void wr_com(uchar com)
  74. { delay1ms(1);
  75.    RS=0;
  76.    RW=0;
  77.    EN=0;
  78.    P0=rolmove(com);
  79.    delay1ms(1);
  80.    EN=1;
  81.    delay1ms(1);
  82.    EN=0;
  83. }

  84. void wr_dat(uchar dat)
  85. { delay1ms(1);;
  86.    RS=1;
  87.    RW=0;
  88.    EN=0;
  89.    P0=rolmove(dat);
  90.    delay1ms(1);
  91.    EN=1;
  92.    delay1ms(1);
  93.    EN=0;
  94. }
  95. /*****************************液晶初始化*********************************************/
  96. void lcd_init()
  97. {        delay1ms(15);
  98.         wr_com(0x38);delay1ms(5);
  99.         wr_com(0x08);delay1ms(5);
  100.         wr_com(0x01);delay1ms(5);
  101.          wr_com(0x06);delay1ms(5);
  102.         wr_com(0x0c);delay1ms(5);
  103.         wr_com(0x80);
  104.     wr_dat('P');//
  105.         wr_com(0x81);
  106.     wr_dat('M');//:
  107.           wr_com(0x82);
  108.     wr_dat(':');

  109.         wr_com(0x87);
  110.     wr_dat('m');
  111.         wr_com(0x88);
  112.     wr_dat('g');
  113.           wr_com(0x89);
  114.     wr_dat('/');
  115.         wr_com(0x8a);
  116.     wr_dat('m');
  117.         wr_com(0x8b);
  118.     wr_dat('3');

  119.           wr_com(0xc0);
  120.     wr_dat('A');
  121.           wr_com(0xc1);
  122.     wr_dat('L');
  123.           wr_com(0xc2);
  124.     wr_dat(':');
  125.         wr_com(0xc7);
  126.     wr_dat('m');
  127.         wr_com(0xc8);
  128.     wr_dat('g');
  129.           wr_com(0xc9);
  130.     wr_dat('/');
  131.         wr_com(0xca);
  132.     wr_dat('m');
  133.         wr_com(0xcb);
  134.     wr_dat('3');
  135.             
  136. }
  137. /*****************显示函数******************************/
  138. void disp(unsigned int Data)
  139. {
  140.   uint Temp;
  141.    Temp=Data%10000;
  142.    str[0]=Temp/1000+0x30;   
  143.    Temp%=1000;
  144.    str[1]='.';
  145.    str[2]=Temp/100+0x30;           
  146.    Temp%=100;
  147.    str[3]=Temp/10+0x30;         
  148.    str[4]=Temp%10+0x30;           

  149.     wr_com(0x83);
  150.     wr_dat(str[0]);
  151.     wr_com(0x84);
  152.     wr_dat(str[1]);
  153.     wr_com(0x85);
  154.     wr_dat(str[2]);
  155.     wr_com(0x86);
  156.     wr_dat(str[3]);

  157. }
  158. /************************显示************************************/
  159. void baojing()
  160. {
  161.         wr_com(0xc3);
  162.     wr_dat(tab[0]+0x30);
  163.         wr_com(0xc4);
  164.     wr_dat(tab[1]);
  165.          wr_com(0xc5);
  166.     wr_dat(tab[2]+0x30);
  167.         wr_com(0xc6);
  168.     wr_dat(tab[3]+0x30);

  169.         wr_com(0x8d);
  170.     wr_dat(str1[0]);
  171.         wr_com(0x8e);
  172.     wr_dat(str1[1]);
  173.         wr_com(0x8f);
  174.     wr_dat('%');
  175.         wr_com(0xcd);
  176.     wr_dat(str2[0]);
  177.           wr_com(0xce);
  178.     wr_dat(str2[1]);
  179.         wr_com(0xcf);
  180.     wr_dat('C');
  181. }
  182. /*****延时子程序*****/
  183. void Delay(uint num)
  184. {
  185. while( --num );
  186. }
  187. /**************************按键检测*******************************************/
  188. void checkkey()
  189. {
  190.         if(SET==0)
  191.                 {
  192.                    Delay(2000);
  193.                    do{}while(SET==0);
  194.                    set_st++;
  195.                    if(set_st>1)set_st=0;
  196.                 }
  197.         if(set_st==0)
  198.                 {
  199.                  
  200.                 }
  201. else if(set_st==1)
  202.         {
  203.                         if(DEC==0)
  204.                         {
  205.                                 Delay(2000);
  206.                                    do{}while(DEC==0);
  207.                                 
  208.                                 if(DUST_SET>0)DUST_SET--;
  209.                                 if(DUST_SET==0)DUST_SET=0;
  210.                         }
  211.                         if(ADD==0)
  212.                         {
  213.                                 Delay(2000);
  214.                                    do{}while(ADD==0);
  215.                                 DUST_SET++;
  216.                                 if(DUST_SET>80)DUST_SET=80;
  217.                         }
  218.         }

  219. tab[0]=DUST_SET/100;
  220. tab[1]='.';
  221. tab[2]=DUST_SET%100/10;
  222. tab[3]=DUST_SET%100%10;
  223. }
  224. /*****报警子程序*****/
  225. void Alarm()
  226. {
  227. if(x>=5){beep_st=~beep_st;x=0;}

  228. if(DUST/10>DUST_SET&&beep_st==1)BEEP=1;
  229.         else BEEP=0;

  230. }
  231. /**************************AD0832转换程序***********************************************/
  232. uchar ADC0832(bit mode,bit channel)     
  233. {
  234.         uchar i,dat,ndat;
  235.         
  236.         ADCS = 0;
  237.         _nop_();
  238.         _nop_();
  239.         
  240.         ADDI = 1;        
  241.         ADCLK = 1;
  242.         _nop_();
  243.         _nop_();
  244.         ADCLK = 0;
  245.         _nop_();
  246.         _nop_();
  247.         
  248.         ADDI = mode;               
  249.         ADCLK = 1;
  250.         _nop_();
  251.         _nop_();
  252.         ADCLK = 0;
  253.         _nop_();
  254.         _nop_();
  255.         
  256.         ADDI = channel;        
  257.         ADCLK = 1;
  258.         _nop_();
  259.         _nop_();
  260.         ADCLK = 0;
  261.         
  262.         ADDI = 1;
  263.         dat = 0;
  264.         
  265.         for(i = 0;i < 8;i++)
  266.         {
  267.                 dat <<= 1;
  268.                 ADCLK=1;
  269.                 _nop_();
  270.                 _nop_();
  271.                 ADCLK=0;
  272.                 _nop_();
  273.                 _nop_();
  274.                 dat |= ADDO;
  275.         }
  276.         ndat = 0;            //记录D0
  277.         if(ADDO == 1)
  278.         ndat |= 0x80;
  279.         
  280.         for(i = 0;i < 7;i++)
  281.         {
  282.                 ndat >>= 1;
  283.                 ADCLK = 1;
  284.                 _nop_();
  285.                 _nop_();
  286.                 ADCLK=0;
  287.                 _nop_();
  288.                 _nop_();
  289.                 if(ADDO==1)
  290.                 ndat |= 0x80;
  291.         }         
  292.         ADCS=1;
  293.         ADCLK=0;
  294.         ADDI=1;
  295.         if(dat==ndat)
  296.         return(dat);
  297.         else
  298.         return 0;   
  299. }
  300. /*****定时器0中断服务程序*****/
  301. void timer0(void) interrupt 1
  302. {
  303.           uint j;        
  304.         TL0 = (65536-10000)/256;
  305.         TH0 = (65536-10000)%256;   
  306.             LED=1;                                         
  307.                 x++;
  308.      for (j=0;j<30;j++);  
  309.         abc=ADC0832(1,0);        
  310.         //num++;
  311.         //if(num>0)
  312.         //{
  313.           FlagStart=1;
  314.           //num=0;
  315.           TR0 = 0;   
  316.           EA = 0;
  317.         LED1=~LED1;
  318.         //}

  319.         LED=0;
  320. }
  321. //中值滤波
  322. //算法:先进行排序,然后将数组的中间值作为当前值返回。
  323. uchar Error_Correct(uchar *str,uchar num)
  324. {
  325.    unsigned char i=0;
  326.    unsigned char j=0;
  327.    uchar Temp=0;
  328.    
  329.    //排序
  330.    for(i=0;i<num-1;i++)
  331.      {
  332.           for(j=i+1;j<num;j++)
  333.            {
  334.              if(str[i]<str[j])
  335.                    {
  336.                    Temp=str[i];
  337.                    str[i]=str[j];
  338.                    str[j]=Temp;
  339.                
  340.                 }
  341.            
  342.            }
  343.         }
  344.     //去除误差,取中间值
  345.     return str[num/2];

  346. }
  347. void DelayUs(unsigned char us)//delay us
  348. {
  349. unsigned char uscnt;
  350. uscnt=us>>1;
  351. while(--uscnt);
  352. }
  353. /******************************************************************/
  354. void DelayMs(unsigned char ms)//delay Ms
  355. {
  356. while(--ms)
  357.    {
  358.      DelayUs(250);
  359.      DelayUs(250);
  360.          DelayUs(250);
  361.          DelayUs(250);
  362.    }
  363. }
  364. /****************************************************************************/
  365. //收发信号检测,数据读取
  366. /****************************************************************************/
  367. char receive()
  368. {   
  369.          unint8 i;
  370.          com_data=0;
  371.          for(i=0;i<=7;i++)   
  372.          {
  373.                   respond=2;
  374.                   while((!TRH)&&respond++);
  375.                   DelayUs(5);
  376.                   DelayUs(5);
  377.                   DelayUs(5);
  378.                   if(TRH)
  379.                   {
  380.                            temp=1;
  381.                            respond=2;
  382.                            while((TRH)&&respond++);
  383.                   }
  384.                   else
  385.                            temp=0;
  386.                   com_data<<=1;
  387.                   com_data|=temp;   
  388.          }
  389.          return(com_data);  
  390. }
  391. /****************************************************************************/
  392. //湿度读取子程序
  393. //温度高8位== TL_data
  394. //温度低8位== TH_data
  395. //湿度高8位== RH_data
  396. //湿度低8位== RH_data
  397. //校验 8位 == CK_data
  398. //调用的程序有 delay();, Delay_5us();,RECEIVE();
  399. /***************************************************************************/
  400. void read_TRH()
  401. {

  402.          
  403.         TRH=0;
  404.         DelayMs(18);
  405.         TRH=1;
  406.         
  407.        DelayUs(5);
  408.        DelayUs(5);
  409.        DelayUs(5);
  410.        DelayUs(5);

  411.       
  412.        TRH=1;
  413.         
  414.       if(!TRH)   
  415.       {
  416.              respond=2;
  417.             
  418.              while((!TRH)&& respond++);
  419.             respond=2;
  420.             
  421.             while(TRH && respond++);
  422.             
  423.             RH_temp = receive();
  424.             RL_temp = receive();
  425.             TH_temp = receive();
  426.             TL_temp = receive();
  427.             CK_temp = receive();
  428.             TRH=1;     
  429.          
  430.              untemp=(RH_temp+RL_temp+TH_temp+TL_temp);
  431.              if(untemp==CK_temp)
  432.             {
  433.                      RH_data = RH_temp;
  434.                      RL_data = RL_temp;
  435.                      TH_data = TH_temp;
  436.                      TL_data = TL_temp;
  437.                      CK_data = CK_temp;
  438.              }
  439.        }
  440.          
  441.          str1[0] = (char)(0X30+RH_data/10);
  442.          str1[1] = (char)(0X30+RH_data%10);
  443.         
  444.          str2[0] = (char)(0X30+TH_data/10);
  445.          str2[1] = (char)(0X30+TH_data%10);
  446.          
  447. }
  448. /*****主函数*****/
  449. void main(void)
  450. {
  451.         InitTimer();   
  452.         LED=1;
  453.         BEEP=0;
  454.         lcd_init();
  455.         delay1ms(100);
  456.         lcd_init();
  457.         delay1ms(100);
  458. while(1)
  459. {

  460. checkkey();
  461. if(set_st==0)
  462. {
  463.         wr_com(0x0c);
  464.             if(FlagStart==1)      
  465.          {
  466.                 num++;
  467.                 ADC_Get[num]=abc;
  468.         if(num>9)
  469.                 {
  470.                          num=0;
  471.                         read_TRH();
  472.                         DUST=Error_Correct(ADC_Get,10);               
  473.                         DUST_Value=(DUST/256.0)*5000;               
  474.                           DUST_Value=DUST_Value*0.17-0.1;
  475.                           if(DUST_Value<0)              DUST_Value=0;
  476.                          if(DUST_Value>760)         DUST_Value=760;        
  477.                           DUST=(uint)DUST_Value;
  478.                 }
  479.           TL0 = (65536-10000)/256;     
  480.           TH0 = (65536-10000)%256;
  481.           TR0 = 1;   
  482.           EA = 1;
  483.           FlagStart=0;
  484.         }
  485.     Alarm();  
  486. }
  487. disp(DUST);
  488. baojing();

  489. if(set_st==1)
  490. {
  491.         wr_com(0xc6);
  492.         wr_com(0x0d);
  493.         delay1ms(150);
  494. }

  495. }
  496. }/*****END*****/
复制代码

所有资料51hei提供下载:
温室度程序及PCB.rar (607.11 KB, 下载次数: 116)


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

使用道具 举报

沙发
ID:438171 发表于 2018-12-5 10:05 | 只看该作者
下载后是一个pm2.5的检测protues,不是温度计的么?
回复

使用道具 举报

板凳
ID:478638 发表于 2020-3-20 22:22 | 只看该作者
您说的NTC在哪儿呢?您的是DHT11啊
回复

使用道具 举报

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

本版积分规则

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

Powered by 单片机教程网

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