久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

標題: 單片機火災報警器電路及程序設計 溫度和氣體檢測 [打印本頁]

作者: 你爸爸哦    時間: 2017-10-27 17:02
標題: 單片機火災報警器電路及程序設計 溫度和氣體檢測
51單片機的火災報警器課設,溫度和氣體檢測
電路原理圖:


主程序流程圖


單片機源程序如下:
  1. //程序頭函數
  2. #include <reg52.h>
  3. //宏定義
  4. #define uint unsigned int
  5. #define uchar unsigned char
  6. //顯示函數
  7. #include <display.h>        //顯示函數display.h在工程里        也可鼠標選中左邊右鍵open document <display.h>
  8. #include <intrins.h>
  9. #include "eeprom52.h"

  10. #define Data_ADC0809 P1                 //定義P1口為Data_ADC0809 (之后的程序里Data_ADC0809即代表P1口)

  11. //管腳聲明
  12. sbit LED_wendu= P2^2;                 //溫度報警燈
  13. sbit LED_yanwu= P2^1;                 //煙霧報警燈
  14. sbit baojing= P2^5;                         //蜂鳴器接口
  15. sbit DQ = P2^0;                                 //ds18b20的數據引腳
  16. //ADC0809
  17. sbit ST=P3^3;
  18. sbit EOC=P3^6;
  19. sbit OE=P3^2;
  20. //按鍵
  21. sbit Key1=P2^6;                                 //設置鍵
  22. sbit Key2=P2^7;                                 //加按鍵
  23. sbit Key3=P3^7;                                 //減按鍵

  24. signed char w;                                     //溫度值全局變量
  25. uint c;                                         //溫度值全局變量
  26. //酒精含量變量
  27. uchar temp;                                         //用于讀取ADC數據
  28. uchar yushe_wendu=5;                 //溫度預設值
  29. uchar yushe_yanwu=45;                 //煙霧預設值
  30. //按鈕模式|  
  31. uchar Mode=0;                                 //=1是設置溫度閥值  =2是設置煙霧閥值

  32. //函數聲明
  33. extern uchar ADC0809();
  34. extern void Key();

  35. /*void delay(uint z)                  //延時函數大約延時z ms
  36. {
  37.         uint i,j;
  38.         for(i=0;i<z;i++)
  39.         for(j=0;j<121;j++);
  40. }                 */

  41. /******************把數據保存到單片機內部eeprom中******************/
  42. void write_eeprom()
  43. {
  44.         SectorErase(0x2000);
  45.         byte_write(0x2000, yushe_wendu);
  46.         byte_write(0x2001, yushe_yanwu);
  47.         byte_write(0x2060, a_a);       
  48. }

  49. /******************把數據從單片機內部eeprom中讀出來*****************/
  50. void read_eeprom()
  51. {
  52.         yushe_wendu   = byte_read(0x2000);
  53.         yushe_yanwu   = byte_read(0x2001);
  54.         a_a      = byte_read(0x2060);
  55. }

  56. /**************開機自檢eeprom初始化*****************/
  57. void init_eeprom()
  58. {
  59.         read_eeprom();                //先讀
  60.         if(a_a != 1)                //新的單片機初始單片機內問eeprom
  61.         {
  62.                 yushe_wendu=50;
  63.                 yushe_yanwu=45;
  64.                 a_a = 1;
  65.                 write_eeprom();           //保存數據
  66.         }       
  67. }

  68. /*****延時子程序:該延時主要用于ds18b20延時*****/
  69. void Delay_DS18B20(int num)
  70. {
  71.   while(num--) ;
  72. }
  73. /*****初始化DS18B20*****/
  74. void Init_DS18B20(void)
  75. {
  76.   unsigned char x=0;
  77.   DQ = 1;         //DQ復位
  78.   Delay_DS18B20(8);    //稍做延時
  79.   DQ = 0;         //單片機將DQ拉低
  80.   Delay_DS18B20(80);   //精確延時,大于480us
  81.   DQ = 1;         //拉高總線
  82.   Delay_DS18B20(14);
  83.   x = DQ;           //稍做延時后,如果x=0則初始化成功,x=1則初始化失敗
  84.   Delay_DS18B20(20);
  85. }
  86. /*****讀一個字節*****/
  87. unsigned char ReadOneChar(void)
  88. {
  89.   unsigned char i=0;
  90.   unsigned char dat = 0;
  91.   for (i=8;i>0;i--)
  92.   {
  93.     DQ = 0;     // 給脈沖信號
  94.     dat>>=1;
  95.     DQ = 1;     // 給脈沖信號
  96.     if(DQ)
  97.     dat|=0x80;
  98.     Delay_DS18B20(4);
  99.   }
  100.   return(dat);
  101. }
  102. /*****寫一個字節*****/
  103. void WriteOneChar(unsigned char dat)
  104. {
  105.   unsigned char i=0;
  106.   for (i=8; i>0; i--)
  107.   {
  108.     DQ = 0;
  109.     DQ = dat&0x01;
  110.     Delay_DS18B20(5);
  111.     DQ = 1;
  112.     dat>>=1;
  113.   }
  114. }
  115. /*****讀取溫度*****/
  116. unsigned int ReadTemperature(void)
  117. {
  118.   unsigned char a=0;
  119.   unsigned char b=0;
  120.   unsigned int t=0;
  121.   float tt=0;
  122.   Init_DS18B20();
  123.   WriteOneChar(0xCC);  //跳過讀序號列號的操作
  124.   WriteOneChar(0x44);  //啟動溫度轉換
  125.   Init_DS18B20();
  126.   WriteOneChar(0xCC);  //跳過讀序號列號的操作
  127.   WriteOneChar(0xBE);  //讀取溫度寄存器
  128.   a=ReadOneChar();     //讀低8位
  129.   b=ReadOneChar();    //讀高8位
  130.   t=b;
  131.   t<<=8;
  132.   t=t|a;
  133.   tt=t*0.0625;
  134.   t= tt*10+0.5;     //放大10倍輸出并四舍五入
  135.   return(t);
  136. }
  137. //=====================================================================================
  138. //=====================================================================================
  139. //=====================================================================================


  140. /*****讀取溫度*****/
  141. void check_wendu(void)
  142. {
  143.         c=ReadTemperature()-5;                          //獲取溫度值并減去DS18B20的溫漂誤差
  144.         if(c<0) c=0;
  145.         if(c>=999) c=999;
  146. }

  147. //ADC0809讀取信息
  148. uchar ADC0809()
  149. {
  150.         uchar temp_=0x00;
  151.         //初始化高阻太

  152.         OE=0;
  153.         //轉化初始化
  154.         ST=0;
  155.         //開始轉換
  156.         ST=1;
  157.         ST=0;
  158.         //外部中斷等待AD轉換結束
  159.         while(EOC==0)
  160.         //讀取轉換的AD值
  161.         OE=1;
  162.         temp_=Data_ADC0809;
  163.         OE=0;
  164.         return temp_;
  165. }

  166. void Key()
  167. {
  168.         //模式選擇
  169.         if(Key1==0)          //設置按鍵
  170.         {
  171.                 while(Key1==0);
  172.                 if(Mode>=3) Mode=0;
  173.                 else
  174.                 {
  175. //                           write_com(0x38);//屏幕初始化
  176.                            write_com(0x0f);//打開顯示 無光標 光標閃爍
  177. //                           write_com(0x06);//當讀或寫一個字符是指針后一一位
  178.                         Mode++;                        //模式加一
  179.                         switch(Mode)        //判斷模式的值
  180.                         {
  181.                                 case 1:
  182.                                 {
  183.                                         write_com(0x80+7);//為1時 溫度閥值的位置閃爍
  184.                                         break;                          //執行后跳出switch
  185.                                 }
  186.                                 case 2:
  187.                                 {
  188.                                         write_com(0x80+15);//為2時 煙霧閥值的位置閃爍
  189.                                         break;
  190.                                 }
  191.                                 case 3:                                        //當模式加到3時
  192.                                 {
  193. //                                        write_com(0x38);//屏幕初始化
  194.                                         write_com(0x0c);//打開顯示 無光標 無光標閃爍
  195.                                         Mode=0;                        //模式清零
  196.                                         break;
  197.                                 }
  198.                         }
  199.                 }
  200.         }
  201.         if(Key2==0&&Mode!=0)         //加按鍵只有在模式不等于0時有效
  202.         {
  203.                 while(Key2==0);
  204.                 switch(Mode)                 //加按鍵按下時 判斷當前模式
  205.                 {
  206.                         case 1:                         //模式為1時
  207.                         {
  208.                                 yushe_wendu++;                                         //預設溫度值(閥值)加1
  209.                                 if(yushe_wendu>=99)                                 //當閥值加到大于等于99時
  210.                                 yushe_wendu=99;                                         //閥值固定為99
  211.                                 write_com(0x80+6);                                 //選中閥值在1602上顯示的位置
  212.                                 write_data(0x30+yushe_wendu/10); //將閥值數據分解開送入液晶顯示
  213.                                 write_data(0x30+yushe_wendu%10);
  214.                                 write_com(0x80+7);
  215.                                 write_eeprom();                           //保存數據
  216.                                 break;
  217.                         }
  218.                         case 2:
  219.                         {
  220.                                 yushe_yanwu++;                                           //同溫度閥值設置
  221.                                 if(yushe_yanwu>=255)
  222.                                 yushe_yanwu=255;
  223.                                 write_com(0x80+13);
  224.                                 write_data(0x30+yushe_yanwu/100);
  225.                                 write_data(0x30+yushe_yanwu%100/10);
  226.                                 write_data(0x30+yushe_yanwu%10);
  227.                                 write_com(0x80+15);
  228.                                 write_eeprom();                           //保存數據
  229.                                 break;                               
  230.                         }
  231.                 }
  232.         }
  233.         if(Key3==0&&Mode!=0)
  234.         {
  235.                 while(Key3==0);
  236.                 switch(Mode)
  237.                 {
  238.                         case 1:
  239.                         {
  240.                                 yushe_wendu--;                                                   //同上
  241.                                 if(yushe_wendu<=0)
  242.                                 yushe_wendu=0;
  243.                                 write_com(0x80+6);
  244.                                 write_data(0x30+yushe_wendu/10);
  245.                                 write_data(0x30+yushe_wendu%10);
  246.                                 write_com(0x80+7);
  247.                                 write_eeprom();                           //保存數據
  248.                                 break;
  249.                         }
  250.                         case 2:
  251.                         {
  252.                                 yushe_yanwu--;                                                          //同上
  253.                                 if(yushe_yanwu<=0)
  254.                                 yushe_yanwu=0;
  255.                                 write_com(0x80+13);
  256.                                 write_data(0x30+yushe_yanwu/100);
  257.                                 write_data(0x30+yushe_yanwu%100/10);
  258.                                 write_data(0x30+yushe_yanwu%10);
  259.                                 write_com(0x80+15);
  260.                                 write_eeprom();                           //保存數據
  261.                                 break;                               
  262.                         }
  263.                 }
  264.         }
  265. //        delay(200);                                                                                           //延時
  266. //        write_com(0x38);//屏幕初始化
  267. //        write_com(0x0c);//打開顯示 無光標 無光標閃爍
  268. }
  269. /*****主函數*****/
  270. void main()
  271. {
  272.         check_wendu();                  //初始化時調用溫度讀取函數 防止開機85°C
  273.         check_wendu();
  274.         init_eeprom();  //開始初始化保存的數據
  275.         Init1602();                          //調用初始化顯示函數
  276.         while(1)                          //進入循環
  277.         {
  278.                 temp=ADC0809();          //讀取煙霧值
  279.                 check_wendu();          //讀取溫度值
  280.                 Key();                          //調用按鍵函數  掃描按鍵

  281.                 if(Mode==0)                  //只有當模式為0時才會執行以下的閥值判斷部分
  282.                 {
  283.                         Display_1602(yushe_wendu,yushe_yanwu,c,temp);  //顯示預設溫度,預設煙霧,溫度值,煙霧值
  284.                         if(temp>=yushe_yanwu)          //煙霧值大于等于預設值時
  285.                         {
  286.                                 LED_yanwu=0;                  //煙霧指示燈亮
  287.                                 baojing=0;                          //蜂鳴器報警
  288.                         }
  289.                         else                                          //煙霧值小于預設值時
  290.                         {
  291.                                 LED_yanwu=1;                  //關掉報警燈
  292.                         }
  293.                         if(c>=(yushe_wendu*10))          //溫度大于等于預設溫度值時(為什么是大于預設值*10:因為我們要顯示的溫度是有小數點后一位,是一個3位數,25.9°C時實際讀的數是259,所以判斷預設值時將預設值*10)
  294.                         {
  295.                                 baojing=0;                          //打開蜂鳴器報警
  296.                                 LED_wendu=0;                  //打開溫度報警燈
  297.                         }
  298.                         else                                          //溫度值小于預設值時
  299.                         {
  300.                                 LED_wendu=1;                  //關閉報警燈
  301.                         }
  302.                         if((temp<yushe_yanwu)&&(c<(yushe_wendu*10)))          //當煙霧小于預設值并且溫度也小于預設值時 (&&:邏輯與,左右兩邊的表達式都成立(都為真,也就是1)時,該if語句才成立)
  303.                         {
  304.                                 baojing=1;                          //停止報警
  305.                         }
  306.                 …………限于本文篇幅 余下代碼請從51黑下載附件…………
復制代碼



所有資料51hei提供下載:
1-c程序 注釋.rar (279.68 KB, 下載次數: 292)



作者: 一個人丶一座城    時間: 2017-11-16 10:00
很強勢 謝謝了
作者: Nancynoha    時間: 2017-11-17 12:19
好東西 謝謝了
作者: 694073644    時間: 2018-6-20 15:21
因為我們要顯示的溫度是有小數點后一位,是一個3位數,25.9°C時實際讀的數是259,所以判斷預設值時將預設值*10
作者: FLY581    時間: 2018-9-30 10:51
謝謝分享
作者: TJW。    時間: 2018-11-14 19:41
挺好的
作者: 時光ning    時間: 2018-12-13 21:16
怎么沒有dsk文件啊
作者: Evelynchan    時間: 2019-3-13 17:28
請問如果要加水泵和風扇怎么操作呀




歡迎光臨 (http://www.zg4o1577.cn/bbs/) Powered by Discuz! X3.1
主站蜘蛛池模板: 亚洲精品一 | 亚洲综合视频 | 精品久久久久久国产 | 中文字幕第100页 | 国产女人与拘做视频免费 | 天天操网 | 国产高清免费 | 国产成人久久 | 精品一区二区在线看 | 亚洲一区导航 | 精精国产xxxx视频在线 | 日韩欧美视频 | 日韩国产一区二区三区 | 国产成人久久精品一区二区三区 | 久久精品国产一区二区电影 | 日本精品一区二区三区视频 | 国产精品久久国产愉拍 | 天天综合网天天综合 | 日韩免费网站 | 成人影院一区二区三区 | 国产精品久久久久一区二区 | 国产精品久久久久久妇女6080 | 国产精品久久久久久久久免费软件 | 男女网站免费观看 | 91精品在线观看入口 | 久热伊人| 视频一区 国产精品 | 国产精品一区二区久久 | 男人影音 | 日本三级线观看 视频 | 91精品久久久久 | 欧美精品一区二区三区在线播放 | 在线一区 | 精品视频免费 | 欧美激情视频一区二区三区在线播放 | 成人性视频免费网站 | 久久久久成人精品 | 午夜精品福利视频 | 欧美老少妇一级特黄一片 | 久久精品99久久 | 在线一级片 |