⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 main.c

📁 天然气报警器 采用51控制 可以控制2路开关
💻 C
字号:
#include "STC89C51RC_RD_PLUS.H" 
#include "LCD_DRV.h "
#include "TIME_DRV.h "

sbit BEEP=P2^2;            	
sbit LED=P2^3;    
sbit FAN1=P2^0;
sbit FAN2=P2^1;

//sbit SensorLED=P1^6;

unsigned char Flag;       //主程序处理标志
unsigned char SetIndex;	 //工作设置索引号
unsigned char DateFlag;   //日期——时间分时显示标志

unsigned char Fan1Flag;	//继电器1#动作标志
unsigned char Fan2Flag;	//继电器2#动作标志

unsigned char Set='1';	     //显示的设置菜单编号(ascii码)

unsigned char SensorInit; 	 //传感器初始化标志
unsigned char InitDelay;	 //传感器初始化延时时间标志
unsigned char FirstCheck;	 //传感器首次检测标志
unsigned char StateFlag;	 //传感器状态标志

unsigned char NotWork1,NotWorkFlag,NotWork2; // 传感器未工作判断标志组

unsigned char Count1;	   
unsigned char BeepFlag;		   //蜂鸣器标志

unsigned char FanDelay;		   //设备延时关断标志
unsigned char Count2;

unsigned char PauseTime;		//暂停刷新时间
unsigned char WDTFlag;			//软狗标志
////////////////////////////////////////////////////////////////////////////
/*=============================分界线=====================================*/
///////////////////////////////////////////////////////////////////////////
/*
1HZ  0号中断  : void Check() interrupt 0
TIME2中断程序 :	void Time2() interrupt 5
键盘中断程序1 :	void Key_1() interrupt 6
键盘中断程序2 :	void Key_2() interrupt 7
=======================================================================*/
void Check() interrupt 0
{ 
if(WDTFlag==1){WDT_CONTR=0x3c;WDTFlag=0;}  //软狗正常,才喂硬狗

if(PauseTime==0)
{
ReadTime();						 //刷新时间
if(DateFlag++>10)Flag=02;		 //每10秒分时显示日期——时间
else Flag=01;
}

if(SensorInit==1){if(InitDelay++>30){SensorInit=0;LED=0;}}	//传感器初始化标志置位,延时30秒撤除标志,开始检测
if(NotWorkFlag==1)NotWork2++;	  // 传感器未工作标志置位

}
//======================================================================

void Time2() interrupt 5
{
if(FanDelay==1)Count2++;
if(Count1++>3){LED=~LED;Count1=0;if(BeepFlag==1)BEEP=~BEEP; }


TF2=0;                           //STC TIME2中断标志需软件清除
}
//======================================================================

void Key_1() interrupt 6
{
 Delay(2000);
if(P1!=0xff)Flag=03;
 }
//======================================================================
void Key_2() interrupt 7
{
 Delay(2000);
if(P1!=0xff)Flag=03;
 }


////////////////////////////////////////////////////////////////////////////
/*=============================分界线=====================================*/
///////////////////////////////////////////////////////////////////////////
/*
                      日期——时间显示程序

=======================================================================*/
void DisplayTime(void)
{
PutChar((Date[0]&0x0f)+0x30,12,1); PutChar(((Date[0]&0x7f)>>4)+0x30,14,0);
PutChar((Date[1]&0x0f)+0x30,16,1); PutChar(((Date[1]&0x7f)>>4)+0x30,18,1);
PutChar((Date[2]&0x0f)+0x30,22,1); PutChar(((Date[2]&0x3f)>>4)+0x30,24,0);	
} 
//========================================================================
void DisplayDate(void)
{
PutChar((Date[3]&0x0f)+0x30,12,1); PutChar(((Date[3]&0x3f)>>4)+0x30,14,0);
PutChar((Date[4]&0x0f)+0x30,16,0); PutChar(((Date[4]&0x1f)>>4)+0x30,18,1);
PutChar((Date[5]&0x0f)+0x30,22,0); PutChar(((Date[5])>>4)+0x30,24,0);
} 


////////////////////////////////////////////////////////////////////////////
/*=============================分界线=====================================*/
///////////////////////////////////////////////////////////////////////////
/*
                      键盘处理程序
主处理程序          :void KeySet(void)
更改时间+           :void AddTime(void)
更改时间-           :void DecTime(void)
显示调整值          :void AdjDisplay(uint8 time,uint8 add)
重新运行调整后的时间: void RunTime(void)

=======================================================================*/
void RunTime(void)
{
 
 ClearLCD();/*IT0=1;EX0=1;*/PauseTime=0;Set='1';SetIndex=0;
}
//========================================================================
void AdjDisplay(uint8 time,uint8 add)
{
PutChar((time&0x0f)+0x30,add,1); PutChar(((time&0x7f)>>4)+0x30,add+2,0);
}

//========================================================================
void AddTime(void)
{
 switch (SetIndex)
 {
 case 1:if((Date[1]&0x7f)==0x59)Date[1]=0xff;                //判断是否大于59
        if((Date[1]&0x0f)==0x09)Date[1]+=0x06;++Date[1];	  // 判断是否各位大于9
		 AdjDisplay(Date[1],16);break;                        //分

 case 2:if((Date[2]&0x3f)==0x23)Date[2]=0xff;               
        if((Date[2]&0x0f)==0x09)Date[2]+=0x06;++Date[2];	  
		 AdjDisplay(Date[2],22);break;                        //时
 
 }
}
//========================================================================
void DecTime(void)
{
 switch (SetIndex)
 {
  case 1:if((Date[1]&0x7f)==0x00)Date[1]=0x60; 	  //判断是否小于00
        if((Date[1]&0x0f)==0x00)Date[1]-=0x06;--Date[1];	  // 判断是否各位小于0
         AdjDisplay(Date[1],16);break;

  case 2:if((Date[2]&0x3f)==0x00)Date[2]=0x24; 	  
        if((Date[2]&0x0f)==0x00)Date[2]-=0x06;--Date[2];	 
         AdjDisplay(Date[2],22);break;
 }
}
//========================================================================

void KeySet(void)
{ 

 switch (P1&0x3f)
{
 case 0x3e:	 PauseTime=1;//IT0=0;EX0=0;	
             Display(0x00,2,0x3d);Display(0x00,4,0x1f);
             Display(0x00,6,0x93);PutChar(Set++,0,0);
			 SetIndex++;DisplayTime();if(SetIndex>2)RunTime();break;			//设置选择

 case 0x3d: if(SetIndex!=0)AddTime();break;										//时间加

 case 0x3b:	if(SetIndex!=0)DecTime();break;										//时间减

 case 0x37:	 if(SetIndex!=0){WriteTime(); RunTime();}break; 	                //确认设置
              
 case 0x1f:	 FAN1=~FAN1;if(FAN1==1)Display(0x00,20,(Fan1Flag=0x10));			//继电器手动1#
             else Fan1Flag=0x00; Display(0x00,20,(Fan1Flag|Fan2Flag));break;

 case 0x2f:	 FAN2=~FAN2;if(FAN2==1)Display(0x00,20,(Fan2Flag=0x40));			//继电器手动2#
             else Fan2Flag=0x00; Display(0x00,20,(Fan1Flag|Fan2Flag));break;
 }
}
////////////////////////////////////////////////////////////////////////////
/*=============================分界线=====================================*/
////////////////////////////////////////////////////////////////////////////
/*
                      传感器状态检测程序
报警状态动作:  void Action(unsigned char mode,unsigned char fan)
正常状态检测:  void CheckState(void)
报警状态恢复:  void RenewState(void)
传感器未工作: void NotWorkCheck(void)
=======================================================================*/
void Action(unsigned char level,unsigned char fan)
{
 if(fan==1){FAN1= 1;FAN2= 1;BeepFlag=1;}else {FAN1= 1;}
 ET2=1; TR2=1;StateFlag=1;FanDelay=0;Count2=0;
 PutChar('0',2,0);PutChar(level,4,0);Display(0x00,20,0x50);
}

//=======================================================================	  		
void CheckState(void)
{
 EA=0;
 switch(P2&0XF0)
     {											    
										       
      case 0x80:											   
	             if(FirstCheck==1){LED=1;Display(0x00,20,0x80);}	//上电只检测一次故障:工作状态非正常		     
                  else {Action('3',1);}break;		  		
	  case 0xb0:	                                         //告警:1#
	             Action('1',0);break;
	  case 0x90:				                             //告警:2#
	             Action('2',1);break;		  	
      }
	  EA=1;FirstCheck=0;
}
//==============================================================================

void RenewState(void)
{ 
  EA=0;
  if((P2&0XF0)==0XF0)FanDelay=1;	
    
   if(Count2>100){
	               ET2=0; TR2=0;StateFlag=0;FanDelay=0;Count2=0; FAN1=0; FAN2=0;BeepFlag=0;
		           LED=0;BEEP=0; Display(0x00,2,0x00);Display(0x00,4,0x00);Display(0x00,20,0x00);StateFlag=0;
	              }
     
  EA=1;
}

//==============================================================================
 /*因传感器工作状态有可能震荡(0~2.5v之间)	故在第一次检测到未工作状态时
  延时6秒,如恢复正常则是在震荡状态,反之传感器出现故障!
  具体为:置位NotWorkFlag,使NotWork2在中断中计数,如果NotWork1与NotWork2不等
  则判断不是连续6次出现未工作状态,反之6秒内工作状态均不正常,即可做出判断*/
//==============================================================================	
void NotWorkCheck(void)
{
 if((P2&0XF0)==0x70)  //故障:未工作
      {	
	            NotWorkFlag=1;if(NotWork1==NotWork2)
				   {if((NotWork1++) >6)
				      {while(1)
				         {Delay(30000);BEEP=~BEEP;LED=~LED;WDTFlag=1;}
				      }
				   }
				 else 	{NotWork1=0,NotWorkFlag=0,NotWork2=0;}
		}
 }


 

////////////////////////////////////////////////////////////////////////////
/*=============================分界线=====================================*/
/////////////////////////////////main///////////////////////////////////////
void main()
{
 
 
 PCF8576Init();		              //显示初始化 
 PCF8563Init();					  //时间初始化
 Delay(5000);				  
 BEEP=0;
 FAN1=0;
 FAN2=0;
 
 SensorInit=1;					  //传感器初始化标志置位
 FirstCheck=1;
 EA=1;
 IT0=1;
 EX0=1;
 //IT1=1;
 //EX1=1;
 IT2=1;
 EX2=1;
 IT3=1;
 EX3=1;

 RCAP2L= 0x00;                      //T2定时器70毫秒初值
 RCAP2H= 0x40;
 T2CON= 0x00;

 WDT_CONTR=0x3c;				   //开狗
   
 while(1) 
 {
   WDTFlag=1;														 //软狗置位
   if(SensorInit==0){if(StateFlag==1)RenewState();CheckState(); }	 //主检测任务

  switch (Flag)
   {																 
     case 01:DisplayTime();if(SensorInit==0)NotWorkCheck(); Flag=0;break;//时间显示
     case 02:DisplayDate();Flag=0;if(DateFlag>13)DateFlag=0;break;		 //日期显示
     case 03:KeySet();Flag=0;break;				                         //键盘处理


    
   }
  }
}



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -