本帖最后由 清泉映殘月 于 2020-4-20 19:54 編輯
學習51單片機C語言編程6天,成功實現通過液晶實時顯示周圍環境溫濕度,當與所設溫濕度區間不符立即蜂鳴報警(報警音是---八月桂花 ),具有一鍵報警消音功能,設置鍵按一次設置濕度上限,兩次濕度下限,三次溫度上限,四次溫度下限,五次退出設置部分代碼如下
- /*-----------------------------------------------
- 硬件:單片機AT89C52、液晶1602、溫濕傳感器DHT11、晶振11.0592M
- 功能:實時顯示周圍環境溫濕度,與所設溫濕度區間不符立即蜂鳴報警,
- 具有報警消音功能,s1循環設置,s2加,s3減,s4報警消音
- 通訊連接:P0口與液晶1602通訊,P3.7口與溫濕傳感器DHT11通訊連接
- ------------------------------------------------*/
- #include <reg52.h> //包含頭文件,一般情況不需要改動,頭文件包含特殊功能寄存器的定義
- #include <intrins.h>
- #include <math.h>
- #define uchar unsigned char
- #define uint unsigned int
- sbit RS = P2^3; //定義端口
- sbit RW = P2^4;
- sbit EN = P2^5;
- sbit Data = P3^7;//定義數據線
- sbit moshi=P2^6; //模式切換
- sbit INC=P2^7; //加
- sbit DEC=P2^0; //減
- sbit SPK=P3^6; //蜂鳴報警
- sbit XY=P2^1; //蜂鳴報警消音
- uchar rec_dat0[16]; //用于顯示的接收數據數組
- uchar rec_dat1[16];
- uchar countRH=95,countRL=20,moshicount=0,n=0;//n為報警音樂節拍常數變量
- uchar RH,RL,TH,TL;
- char countTH=50,countTL=0;
- void xiaoyin();
- unsigned char code music_tab[] ={
- 0x18, 0x30, 0x1C , 0x10, //格式為: 頻率常數, 節拍常數, 頻率常數, 節拍常數,
- 0x20, 0x40, 0x1C , 0x10,
- 0x18, 0x10, 0x20 , 0x10,
- 0x1C, 0x10, 0x18 , 0x40,
- 0x1C, 0x20, 0x20 , 0x20,
- 0x1C, 0x20, 0x18 , 0x20,
- 0x20, 0x80, 0xFF , 0x20,
- 0x30, 0x1C, 0x10 , 0x18,
- 0x20, 0x15, 0x20 , 0x1C,
- 0x20, 0x20, 0x20 , 0x26,
- 0x40, 0x20, 0x20 , 0x2B,
- 0x20, 0x26, 0x20 , 0x20,
- 0x20, 0x30, 0x80 , 0xFF,
- 0x20, 0x20, 0x1C , 0x10,
- 0x18, 0x10, 0x20 , 0x20,
- 0x26, 0x20, 0x2B , 0x20,
- 0x30, 0x20, 0x2B , 0x40,
- 0x20, 0x20, 0x1C , 0x10,
- 0x18, 0x10, 0x20 , 0x20,
- 0x26, 0x20, 0x2B , 0x20,
- 0x30, 0x20, 0x2B , 0x40,
- 0x20, 0x30, 0x1C , 0x10,
- 0x18, 0x20, 0x15 , 0x20,
- 0x1C, 0x20, 0x20 , 0x20,
- 0x26, 0x40, 0x20 , 0x20,
- 0x2B, 0x20, 0x26 , 0x20,
- 0x20, 0x20, 0x30 , 0x80,
- 0x20, 0x30, 0x1C , 0x10,
- 0x20, 0x10, 0x1C , 0x10,
- 0x20, 0x20, 0x26 , 0x20,
- 0x2B, 0x20, 0x30 , 0x20,
- 0x2B, 0x40, 0x20 , 0x15,
- 0x1F, 0x05, 0x20 , 0x10,
- 0x1C, 0x10, 0x20 , 0x20,
- 0x26, 0x20, 0x2B , 0x20,
- 0x30, 0x20, 0x2B , 0x40,
- 0x20, 0x30, 0x1C , 0x10,
- 0x18, 0x20, 0x15 , 0x20,
- 0x1C, 0x20, 0x20 , 0x20,
- 0x26, 0x40, 0x20 , 0x20,
- 0x2B, 0x20, 0x26 , 0x20,
- 0x20, 0x20, 0x30 , 0x30,
- 0x20, 0x30, 0x1C , 0x10,
- 0x18, 0x40, 0x1C , 0x20,
- 0x20, 0x20, 0x26 , 0x40,
- 0x13, 0x60, 0x18 , 0x20,
- 0x15, 0x40, 0x13 , 0x40,
- 0x18, 0x80, 0x00
- };
- #define RS_CLR RS=0
- #define RS_SET RS=1
-
- #define RW_CLR RW=0
- #define RW_SET RW=1
-
- #define EN_CLR EN=0
- #define EN_SET EN=1
-
- #define DataPort P0
-
-
- /*------------------------------------------------
- uS延時函數,含有輸入參數 unsigned char t,無返回值
- unsigned char 是定義無符號字符變量,其值的范圍是
- 0~255 這里使用晶振12M,精確延時請使用匯編,大致延時
- 長度如下 T=tx2+5 uS
- ------------------------------------------------*/
- void DelayUs2x(unsigned int t)
- {
- while(--t);
- }
- /*------------------------------------------------
- mS延時函數,含有輸入參數 unsigned char t,無返回值
- unsigned char 是定義無符號字符變量,其值的范圍是
- 0~255 這里使用晶振12M,精確延時請使用匯編
- ------------------------------------------------*/
- void DelayMs(unsigned char t)
- {
-
- while(t--)
- {
- //大致延時1mS
- DelayUs2x(245);
- DelayUs2x(245);
- }
- }
- void delay (unsigned char m) //控制頻率延時
- {
- unsigned i=3*m;
- while(--i);
- }
- /*------------------------------------------------
- 判忙函數
- ------------------------------------------------*/
- bit LCD_Check_Busy(void)
- {
- DataPort= 0xFF;
- RS_CLR;
- RW_SET;
- EN_CLR;
- _nop_();
- EN_SET;
- return (bit)(DataPort & 0x80);
- }
- /*------------------------------------------------
- 寫入命令函數
- ------------------------------------------------*/
- void LCD_Write_Com(unsigned char com)
- {
- while(LCD_Check_Busy()); //忙則等待
- RS_CLR;
- RW_CLR;
- EN_SET;
- DataPort= com;
- _nop_();
- EN_CLR;
- }
- /*------------------------------------------------
- 寫入數據函數
- ------------------------------------------------*/
- void LCD_Write_Data(unsigned char Data)
- {
- while(LCD_Check_Busy()); //忙則等待
- RS_SET;
- RW_CLR;
- EN_SET;
- DataPort= Data;
- _nop_();
- EN_CLR;
- }
-
- /*------------------------------------------------
- 寫入字符函數
- ------------------------------------------------*/
- void LCD_Write_Char(unsigned char x,unsigned char y,unsigned char Data)
- {
- if (y == 1)
- {
- LCD_Write_Com(0x80 + x);
- }
- else
- {
- LCD_Write_Com(0xC0 + x);
- }
- LCD_Write_Data( Data);
- }
- /*------------------------------------------------
- 初始化函數
- ------------------------------------------------*/
- void LCD_Init(void)
- {
- LCD_Write_Com(0x38); //設置 8 位格式,2 行,5x7
- LCD_Write_Com(0x0C); //整體顯示,關光標,不閃爍
- LCD_Write_Com(0x06); //寫一個字符后地址指針加 1,設定輸入方式,增量不移位
- LCD_Write_Com(0x01); //清除屏幕顯示
- DelayMs(5);
- }
- //*******定時器初始化函數**********
- void timerinit() //采用中斷0 控制節拍
- {
- TMOD=0x01;//設置定時器0為工作方式1
- TH0=0xd8;
- TL0=0xef;
- EA=1; //開總中斷
- ET0=1;//開定時器0中斷
- }
- //********************************
-
- /*------------------------------------------------
- DHT11延時函數
- ------------------------------------------------*/
- void DHT11_delay_us(uchar n)//2微秒延時
- {
- while(--n);
- }
-
- void DHT11_delay_ms(uint z)//1毫秒延時
- {
- uint i,j;
- for(i=z;i>0;i--)
- for(j=110;j>0;j--);
- }
- /*------------------------------------------------
- DHT11開始信號
- ------------------------------------------------*/
- void DHT11_start()
- {
- Data=1;
- DHT11_delay_us(2);
- Data=0;
- DHT11_delay_ms(20); //延時18ms以上
- Data=1;
- DHT11_delay_us(30);
- }
- /*------------------------------------------------
- 接收八位二進制
- ------------------------------------------------*/
- uchar DHT11_rec_byte() //接收一個字節
- {
- uchar i,dat=0;
- for(i=0;i<8;i++) //從高到低依次接收8位數據
- {
- while(!Data); ////等待50us低電平過去
- DHT11_delay_us(8); //延時60us,如果還為高則數據為1,否則為0
- dat<<=1; //移位使正確接收8位數據,數據為0時直接移位
- if(Data==1) //數據為1時,使dat加1來接收數據1
- dat+=1;
- while(Data); //等待數據線拉低
- }
- return dat;
- }
- /*------------------------------------------------
- 接收40bit數據
- ------------------------------------------------*/
- void DHT11_receive() //接收40位的數據
- {
- uchar R_H,R_L,T_H,T_L,revise;
- DHT11_start();
-
- if(Data==0)
- {
-
- while(Data==0); //等待拉高
-
- DHT11_delay_us(40); //拉高后延時80us
- R_H=DHT11_rec_byte(); //接收濕度高八位
- R_L=DHT11_rec_byte(); //接收濕度低八位
- T_H=DHT11_rec_byte(); //接收溫度高八位
- T_L=DHT11_rec_byte(); //接收溫度低八位
- revise=DHT11_rec_byte(); //接收校正位
-
- DHT11_delay_us(25); //結束
-
- if((R_H+R_L+T_H+T_L)==revise) //校正
- {
- RH=R_H;
- RL=R_L;
- TH=T_H;
- TL=T_L;
- rec_dat0[0]=RH/10;
- rec_dat0[1]=RH%10;
- rec_dat1[0]=TH/10;
- rec_dat1[1]=TH%10;
- }
- }
- }
復制代碼
|