找回密碼
 立即注冊(cè)

QQ登錄

只需一步,快速開始

搜索
查看: 4351|回復(fù): 0
打印 上一主題 下一主題
收起左側(cè)

51單片機(jī)Proteus仿真自動(dòng)澆花器+源程序

[復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主
基于51單片機(jī)源程序+仿真-------自動(dòng)澆花器


單片機(jī)源程序如下:
  1. //程序頭函數(shù)
  2. #include <reg52.h>
  3. #include <intrins.h>        //包含頭文件
  4. //顯示函數(shù)
  5. #include <display.h>
  6. #include "eeprom52.h"

  7. //宏定義
  8. #define uint unsigned int
  9. #define uchar unsigned char

  10. //管腳聲明
  11. sbit LED_R= P2^2;                          //紅色指示燈
  12. sbit LED_G= P2^0;                          //綠色指示燈
  13. sbit FENG = P2^5;                          //蜂鳴器
  14. sbit CS   = P1^4;
  15. sbit Clk = P1^2;
  16. sbit DATI = P1^3;
  17. sbit DATO = P1^3;                        //ADC0832引腳

  18. sbit san=P3^4;                                  //繼電器
  19. //按鍵
  20. sbit Key1=P2^6;
  21. sbit Key2=P2^7;
  22. sbit Key3=P3^7;
  23. /*******************************定義全局變量********************************/
  24. unsigned char dat = 0;      //AD值
  25. unsigned char CH=0;       //通道變量
  26. unsigned int sum=0;                         //平均值計(jì)算時(shí)的總數(shù)
  27. unsigned char m=0;
  28. bit bdata flag;                                  //定義位變量
  29. uchar set;                                          //設(shè)置變量
  30. uchar moisture;
  31. uchar full_range=153;
  32. //函數(shù)聲明
  33. extern void Key();
  34. /*
  35. void delay(uint z)
  36. {
  37.         uint i,j;
  38.         for(i=0;i<z;i++)
  39.         for(j=0;j<121;j++);
  40. }
  41. */

  42. //酒精含量變量
  43. uint temp=0;

  44. //指示燈變量

  45. char MH=80,ML=20;                //上下限變量

  46. /******************把數(shù)據(jù)保存到單片機(jī)內(nèi)部eeprom中******************/
  47. void write_eeprom()
  48. {
  49.         SectorErase(0x2000);
  50.         byte_write(0x2000, MH);
  51.         byte_write(0x2001, ML);
  52.         byte_write(0x2060, a_a);        
  53. }

  54. /******************把數(shù)據(jù)從單片機(jī)內(nèi)部eeprom中讀出來*****************/
  55. void read_eeprom()
  56. {
  57.         MH   = byte_read(0x2000);
  58.         ML   = byte_read(0x2001);
  59.         a_a      = byte_read(0x2060);
  60. }

  61. /**************開機(jī)自檢eeprom初始化*****************/
  62. void init_eeprom()
  63. {
  64.         read_eeprom();                //先讀
  65.         if(a_a != 1)                //新的單片機(jī)初始單片機(jī)內(nèi)問eeprom
  66.         {
  67.                 MH  = 80;
  68.                 ML  = 20;
  69.                 a_a = 1;
  70.                 write_eeprom();           //保存數(shù)據(jù)
  71.         }        
  72. }

  73. /****************************************************************************
  74. 函數(shù)功能:AD轉(zhuǎn)換子程序
  75. 入口參數(shù):CH
  76. 出口參數(shù):dat
  77. ****************************************************************************/
  78. unsigned char adc0832(unsigned char CH)
  79. {
  80.         unsigned char i,test,adval;
  81.         adval = 0x00;
  82.         test = 0x00;
  83.         Clk = 0;       //初始化
  84.         DATI = 1;
  85.         _nop_();
  86.         CS = 0;
  87.         _nop_();
  88.         Clk = 1;
  89.         _nop_();
  90.         
  91.         
  92.         if ( CH == 0x00 )      //通道選擇
  93.         {
  94.                 Clk = 0;
  95.                 DATI = 1;      //通道0的第一位
  96.                 _nop_();
  97.                 Clk = 1;
  98.                 _nop_();
  99.                 Clk = 0;
  100.                 DATI = 0;      //通道0的第二位
  101.                 _nop_();
  102.                 Clk = 1;
  103.                 _nop_();
  104.         }
  105.         else
  106.         {
  107.                 Clk = 0;
  108.                 DATI = 1;      //通道1的第一位
  109.                 _nop_();
  110.                 Clk = 1;
  111.                 _nop_();
  112.                 Clk = 0;
  113.                 DATI = 1;      //通道1的第二位
  114.                 _nop_();
  115.                 Clk = 1;
  116.                 _nop_();
  117.         }
  118.         
  119.         Clk = 0;
  120.         DATI = 1;
  121.         for( i = 0;i < 8;i++ )      //讀取前8位的值
  122.         {
  123.                 _nop_();
  124.                 adval <<= 1;
  125.                 Clk = 1;
  126.                 _nop_();
  127.                 Clk = 0;
  128.                 if (DATO)
  129.                 adval |= 0x01;
  130.                 else
  131.                 adval |= 0x00;
  132.         }
  133.         for (i = 0; i < 8; i++)      //讀取后8位的值
  134.         {
  135.                 test >>= 1;
  136.                 if (DATO)
  137.                 test |= 0x80;
  138.                 else
  139.                 test |= 0x00;
  140.                 _nop_();
  141.                 Clk = 1;
  142.                 _nop_();
  143.                 Clk = 0;
  144.         }
  145.         if (adval == test)      //比較前8位與后8位的值,如果不相同舍去。若一直出現(xiàn)顯示為零,請(qǐng)將該行去掉
  146.         dat = test;
  147.         nop_();
  148.         CS = 1;        //釋放ADC0832
  149.         DATO = 1;
  150.         Clk = 1;
  151.         return dat;
  152. }

  153. void init()                                //定時(shí)器初始化函數(shù)
  154. {
  155.         TMOD=0x01;                        //定時(shí)器工作方式
  156.          TL0=0xb0;
  157.          TH0=0x3c;                        //賦初值50ms
  158.          EA=1;                                //打開中斷總開關(guān)
  159.         ET0=1;                                //打開定時(shí)器0中斷允許開關(guān)
  160.          TR0=1;                                //打開定時(shí)器0定時(shí)開關(guān)
  161. }

  162. void main()                                //主函數(shù)
  163. {
  164.         Init1602();                                                 //初始化液晶函數(shù)
  165.         init();                                                         //初始化定時(shí)器
  166.         init_eeprom();  //開始初始化保存的數(shù)據(jù)
  167.         while(1)                                                 //進(jìn)入循環(huán)
  168.         {
  169.                 for(m=0;m<50;m++)                        //讀50次AD值
  170.                 sum = adc0832(0)+sum;                //讀到的AD值,將讀到的數(shù)據(jù)累加到sum
  171.                 temp=sum/50;                                //跳出上面的for循環(huán)后,將累加的總數(shù)除以50得到平均值temp
  172.                 sum=0;                                                 //平均值計(jì)算完成后,將總數(shù)清零
  173.                 if(temp<=full_range)
  174.                 temp=(temp*100)/full_range;
  175.                 else
  176.                 temp=100;
  177.                 if(set==0)                                         //set為0,說明現(xiàn)在不是設(shè)置狀態(tài)
  178.                 Display_1602(temp,MH,ML);         //顯示AD數(shù)值和報(bào)警值
  179.                 if(temp<ML&&set==0)         //AD數(shù)值小于報(bào)警值
  180.                 {
  181.                         flag=1;                                         //打開報(bào)警
  182.                         san=0;
  183.                         LED_G=1;                                          //綠燈熄滅
  184.                         LED_R=0;                                          //紅燈點(diǎn)亮
  185.                 }
  186.                 else if(temp>MH&&set==0)//AD值大于報(bào)警值
  187.                 {
  188.                         flag=0;                                         //關(guān)閉報(bào)警
  189.                         san=1;
  190.                         LED_G=0;                                          //綠燈點(diǎn)亮
  191.                         LED_R=1;                                          //紅燈熄滅
  192.                 }
  193.                 else
  194.                 {
  195.                         flag=0;
  196.                         LED_G=0;                                          //綠燈點(diǎn)亮
  197.                         LED_R=1;                                          //紅燈熄滅
  198.                 }
  199.                 Key();                                                 //調(diào)用按鍵函數(shù)
  200.         }
  201. }

  202. void Key()                                          //按鍵函數(shù)
  203. {
  204.         if(Key1==0)                                  //設(shè)置鍵按下
  205.         {
  206.                 while(Key1==0);                  //按鍵松開
  207.                 FENG=0;                                  //蜂鳴器響
  208.                 set++;                                  //設(shè)置變量加
  209.                 flag=0;                                  //關(guān)閉報(bào)警
  210.                 TR0=0;                                  //關(guān)閉定時(shí)器
  211.         }
  212.         if(set==1)                                  //設(shè)置報(bào)警值時(shí)
  213.         {
  214.                 write_com(0x80+0x40+4);//位置
  215.                    write_com(0x0f);//打開顯示 無光標(biāo) 光標(biāo)閃爍
  216.                 FENG=1;                                //關(guān)閉蜂鳴器
  217.         }
  218.         if(set==2)                                  //設(shè)置報(bào)警值時(shí)
  219.         {
  220.                 write_com(0x80+0x40+14);//位置
  221.                    write_com(0x0f);//打開顯示 無光標(biāo) 光標(biāo)閃爍
  222.                 FENG=1;                                //關(guān)閉蜂鳴器
  223.         }
  224.         else if(set>=3)                //設(shè)置完成時(shí)
  225.         {
  226.                 set=0;                        //變量清零
  227.                 write_com(0x38);//屏幕初始化
  228.                 write_com(0x0c);//打開顯示 無光標(biāo) 無光標(biāo)閃爍
  229.                 FENG=1;                        //關(guān)閉蜂鳴器
  230.                 flag=1;                        //打開報(bào)警
  231.                 TR0=1;                        //打開定時(shí)器
  232.         }
  233.         if(Key2==0&&set!=0)                        //設(shè)置報(bào)警值時(shí)加鍵按下
  234.         {
  235.                 while(Key2==0);                        //按鍵松開
  236.                 FENG=0;                                        //打開蜂鳴器
  237.                 if(set==1)
  238.                 {
  239.                         MH++;                                //報(bào)警值加
  240.                         if(MH>99)                //最大加到255
  241.                         MH=ML+1;                                //清零
  242.                         write_com(0x80+0x40+3);           //選中液晶屏上的第二行第十一列
  243.                         write_data('0'+MH/10);
  244.                         write_data('0'+MH%10);
  245.                         write_com(0x80+0x40+4);//位置
  246.                         FENG=1;                                                //關(guān)閉蜂鳴器
  247.                 }
  248.                 if(set==2)
  249.                 {
  250.                         ML++;                                //報(bào)警值加
  251.                         if(ML>=MH&&MH<99)                //最大加到255
  252.                         MH=ML+1;
  253.                         if(ML>98)
  254.                         ML=0;        
  255.                         write_com(0x80+0x40+3);           //選中液晶屏上的第二行第十一列
  256.                         write_data('0'+MH/10);
  257.                         write_data('0'+MH%10);
  258.                         write_com(0x80+0x40+13);           //選中液晶屏上的第二行第十一列
  259.                         write_data('0'+ML/10);
  260.                         write_data('0'+ML%10);
  261.                         write_com(0x80+0x40+14);//位置
  262.                         FENG=1;                                                //關(guān)閉蜂鳴器
  263.                 }
  264.                 write_eeprom();                           //保存數(shù)據(jù)
  265.         }
  266.         if(Key3==0&&set!=0)                                //注釋同加按鍵
  267.         {
  268.                 while(Key3==0);
  269.                 FENG=0;
  270.                 if(set==1)
  271.                 {
  272.                         MH--;                                //報(bào)警值加
  273.                         if(MH<=ML&&ML>0)                //最大加到255
  274.                         ML=MH-1;                                
  275.                         if(MH<1)
  276.                         MH=99;
  277.                         write_com(0x80+0x40+3);           //選中液晶屏上的第二行第十一列
  278.                         write_data('0'+MH/10);
  279.                         write_data('0'+MH%10);
  280.                         write_com(0x80+0x40+13);           //選中液晶屏上的第二行第十一列
  281.                         write_data('0'+ML/10);
  282.                         write_data('0'+ML%10);
  283.                         write_com(0x80+0x40+4);//位置
  284.                         FENG=1;                                                //關(guān)閉蜂鳴器
  285.                 }
  286.                 if(set==2)
  287.                 {
  288.                         ML--;                                //報(bào)警值加
  289.                         if(ML<0)                //最大加到255
  290.                         ML=MH-1;                                //清零
  291.                         write_com(0x80+0x40+13);           //選中液晶屏上的第二行第十一列
  292.                         write_data('0'+ML/10);
  293.                         write_data('0'+ML%10);
  294.                         write_com(0x80+0x40+14);//位置
  295.                         FENG=1;                                                //關(guān)閉蜂鳴器
  296.                 }
  297.                 write_eeprom();                           //保存數(shù)據(jù)
  298.         }
  299. }

  300. void  time1_int(void) interrupt 1                  //定時(shí)器工作函數(shù)
  301. {
  302.         uchar count;                                                  //定義計(jì)時(shí)變量
  303.         TL0=0xb0;
  304.          TH0=0x3c;                                                          //重新賦初值50ms
  305.           count++;                                                          //變量加一次就是50ms
  306.         if(count==10)                                                  //加到10次就是500ms
  307.         {
  308.                 if(flag==0)                                                  //flag=0時(shí),也就是不開啟報(bào)警
  309.                 FENG=1;                                                  //關(guān)閉蜂鳴器
  310.                 if(flag==1)                                                  //flag為1時(shí),也就是打開報(bào)警
  311.                 FENG=0;                                                  //打開蜂鳴器
  312.         }

  313.            if(count==20)                                                  //計(jì)數(shù)20次,就是1s
  314.            {                                                                          //在1s時(shí),紅綠燈都是熄滅狀態(tài),蜂鳴器也是關(guān)閉狀態(tài),裝可以達(dá)到閃爍的目的
  315.                 count=0;                                                  //變量清零
  316.                 if(flag==0)                                                  //不是報(bào)警狀態(tài)時(shí)
  317.                 FENG=1;
  318.                 if(flag==1)                                                  //報(bào)警狀態(tài)時(shí)
  319.                 FENG=1;
  320.         }
  321. }
復(fù)制代碼

所有資料51hei提供下載:
基于51單片機(jī)自動(dòng)澆花器.rar (3.77 MB, 下載次數(shù): 104)

評(píng)分

參與人數(shù) 1黑幣 +50 收起 理由
admin + 50 共享資料的黑幣獎(jiǎng)勵(lì)!

查看全部評(píng)分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏2 分享淘帖 頂 踩1
回復(fù)

使用道具 舉報(bào)

本版積分規(guī)則

手機(jī)版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術(shù)交流QQ群281945664

Powered by 單片機(jī)教程網(wǎng)

快速回復(fù) 返回頂部 返回列表