天天看點

基于15單片機PWM模拟控制風扇——藍橋杯

        這套試題我覺得是近幾年來相對簡單的一套!裡面沒有使用一些複雜的子產品,有的話可以把DS18B20勉強算上。但是這套試題中,我不知為何要把溫度檢測加上,而且加了溫度以後,并沒有在溫度上做文章,而是進行了顯示,其餘操作并未加入。是以我覺得溫度這塊有點突兀!

        然後控制風扇就使用PWM波來控制,而PWM波用了定時器控制占空比,使單片機輸出不同占空比的PWM波。然後再加了一些花樣的東西就是獨立按鍵控制風扇模式:睡眠風,自然風以及常風三種工作模式。然後再控制定時模式,讓其實作倒計時功能。這就實作了整套題的主要功能。

        閑話不多說,來看看效果和程式吧!

基于15單片機PWM模拟控制風扇——藍橋杯

模式3 常風狀态下倒計時172秒 

基于15單片機PWM模拟控制風扇——藍橋杯

模式4 目前溫度20℃ 

基于15單片機PWM模拟控制風扇——藍橋杯

 模式2 倒計時173秒

#include "STC15F2K60S2.h"
#include "onewire.h"
#define u8 unsigned char


u8 code t_display[]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
u8 code T_COM[]={0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80};
bit key_flag;

#define NO_KEY  0xff  //?????????
#define KEY_STATE0  0   //?ж????????
#define KEY_STATE1  1  //??????????
#define KEY_STATE2  2  //???
unsigned char Key_Scan()
{
 static unsigned char key_state=KEY_STATE0; 
 u8 key_value=0,key_temp;
 u8 key1,key2;
 
 P30=0;P31=0;P32=0;P33=0;P34=1;P35=1;P42=1;P44=1;
 if(P44==0)	key1=0x70;
 if(P42==0)	key1=0xb0;
 if(P35==0)	key1=0xd0;
 if(P34==0)	key1=0xe0;
 if((P34==1)&&(P35==1)&&(P42==1)&&(P44==1))	key1=0xf0;
 
 P30=1;P31=1;P32=1;P33=1;P34=0;P35=0;P42=0;P44=0;
 if(P30==0)	key2=0x0e;
 if(P31==0)	key2=0x0d;
 if(P32==0)	key2=0x0b;
 if(P33==0)	key2=0x07;
 if((P30==1)&&(P31==1)&&(P32==1)&&(P33==1))	key2=0x0f;
 key_temp=key1|key2;
 
 switch(key_state)                                
 {
  case KEY_STATE0:
   if(key_temp!=NO_KEY)
   {
    key_state=KEY_STATE1;               
   }
   break;

  case KEY_STATE1:
   if(key_temp==NO_KEY)
   {
    key_state=KEY_STATE0;
   }
   else
   {
   switch(key_temp)                             
    {
		 case 0x77: key_value=4;break;
		 case 0x7b: key_value=5;break;
		 case 0x7d: key_value=6;break;
         case 0x7e: key_value=7;break;
			
		 case 0xb7: key_value=8;break;
		 case 0xbb: key_value=9;break;
		 case 0xbd: key_value=10;break;
         case 0xbe: key_value=11;break;
			
         case 0xd7: key_value=12;break;
		 case 0xdb: key_value=13;break;
		 case 0xdd: key_value=14;break;
		 case 0xde: key_value=15;break;
			
         case 0xe7: key_value=16;break;
		 case 0xeb: key_value=17;break;
		 case 0xed: key_value=18;break;
		 case 0xee: key_value=19;break;	
    }
    key_state=KEY_STATE2;
   }
   break;
	 
   case KEY_STATE2:
   if(key_temp==NO_KEY)
   {
    key_state=KEY_STATE0;
   }
   break;
 }
 return key_value;
}
void Timer0Init(void)		//[email protected]
{
	AUXR |= 0x80;		//????????1T??
	TMOD &= 0xF0;		//??????????
	TL0 = 0xCD;		//?????????
	TH0 = 0xD4;		//?????????
	TF0 = 0;		//???TF0???
	TR0 = 1;		//?????0??????
	ET0=1;
	EA=1;
}
u8 key_val;
u8 temp_display[8];
u8 work_display[8];
u8 temperature;
u8 mode=1;
u8 time_count;
u8 number;
u8 display_mode;

bit output_flag; 
void main()
{
    P2=0X80;P0=0Xff;P2=0X00;
	P2=0XC0;P0=0X00;P2=0X00;
	Timer0Init();
	while(1)
	{
	   temperature=rd_temperature();
	   temp_display[0]=0x40;
	   temp_display[1]=t_display[4];
	   temp_display[2]=0x40;
	   temp_display[3]=0x00;
	   temp_display[4]=0x00;
	   temp_display[5]=t_display[temperature/10];
	   temp_display[6]=t_display[temperature%10];
	   temp_display[7]=0x39;
	   work_display[0]=0x40;work_display[1]=t_display[mode];work_display[2]=0x40;
	   work_display[3]=0x00;work_display[4]=t_display[time_count/1000];
	   work_display[5]=t_display[time_count/100%10];
	   work_display[6]=t_display[time_count/10%10];
	   work_display[7]=t_display[time_count%10];
	   if(time_count==0)
	   {
	       output_flag=0;
		   P2=0x80;P0=0XFF;P2=0X00;
	   }
	   else
	   {
	       output_flag=1;
	   }
	   if(output_flag)
	   {
		       if(mode==1)
		   {
		       P2=0X80;P0=~0X01;P2=0X00;
		   }
		   if(mode==2)
		   {
		       P2=0X80;P0=~0X02;P2=0X00;
		   }
		   if(mode==3)
		   {
		       P2=0X80;P0=~0X04;P2=0X00;
		   }
	   }
	   if(key_flag)
	   {
	       key_flag=0;
		   key_val=Key_Scan();
		   switch(key_val)
		   {
		       case 4:
			   if(display_mode==0)
			   	  {
				      mode++;
					  if(mode==4)mode=1;
			      }
				  break;
			   case 5:
			   if(display_mode==0)
			   {
			         number++;
					 if(number==1)
					 {
					     time_count=60;
					 }
					 if(number==2)
					 {
					     time_count=120;
					 }
					 if(number==3)
					 {
					     time_count=180;
					 }
					 if(number==4)
					 {
						 time_count=0;
						 number=0;
					 }
			      }
				   break;
			   case 6:
			   if(display_mode==0)
			    {
			   	     time_count=0;
			    }
				break;
			   case 7:
			   	      display_mode++;
					  if(display_mode==2)
					  display_mode=0;
			    break;
		   }
	   } 
	}

}
void Timer0() interrupt 1 using 1
{
    static int key_count=0,smg_count=0,pwm_count=0,time_jian,i=0;
	key_count++;smg_count++;pwm_count++;time_jian++;
	if(key_count==10)
	{
	      key_count=0;
		  key_flag=1;
	}
	if(time_jian==1000)
	{
	     time_jian=0;
		 if(time_count>0)
		 time_count-=1;
	}
	if(smg_count==3)
	{
	      smg_count=0;
		  P2=0XC0;P0=0XFF;P2=0X00;
		  if(display_mode)
		  {
		      P2=0XE0;P0=~temp_display[i];P2=0X00;
		  }
		  else
		  {
		       P2=0XE0;P0=~work_display[i];P2=0X00;
		  }
		  P2=0XC0;P0=T_COM[i];P2=0X00;
		  i++;
		  if(i==8)i=0;
	}
	if(output_flag)
	{
	    if(mode==1)
		{
		    if(pwm_count==8)
			{
			    P34=1;
			}
			if(pwm_count==10)
			{
			    P34=0;
			}
		}
		 if(mode==2)
		{
		    if(pwm_count==7)
			{
			    P34=1;
			}
			if(pwm_count==10)
			{
			    P34=0;
			}
		}
		 if(mode==3)
		{
		    if(pwm_count==3)
			{
			    P34=1;
			}
			if(pwm_count==10)
			{
			    P34=0;
			}
		}
	}
	else
	{
	    pwm_count=0;
		P34=0;
	}
}