目录
第八届省赛主要涉及了DS18B20的运用。还有一些基本外设的应用。
Main.c
#include"STC12C5A60S2.h"
#include"intrins.h"
#include"DS18B20.h"
unsigned char Key_Value;
unsigned char code Tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0xff,0xbf,0xC6};//0,1,2,3,4,5,6,7,8,9,全灭,'-','C'
unsigned char Init_Tab[]={23,59,50};//初始化时间
unsigned char Init_Clock[]={0,0,0};//初始化闹钟时间
unsigned char Time_Set=0,Temper_Set=0;//时间设置和闹钟设置
unsigned int Count=0;//秒计时
unsigned char Flag;//按键按下标志
unsigned char yi,er,san,si,wu,liu,qi=11,ba=11;
unsigned char yi1,er1,san1,si1,wu1,liu1;
unsigned int Time,Time1,Time_Gap=1;//时间间隔,用于闪烁处理
unsigned char Status=0,Shut=0;//Status表示当前状态是时间设置还是闹钟设置。shut代表是否在运转状态
unsigned char Time_Count=0;
long Temper;
bit Key_Press=1;//松手标志
void All_Init()//初始化
{
P2=0XA0;P0=0X00;
P2=0X80;P0=0XFF;
}
void Timer0_Init()//定时器0初始化
{
TH0=0XD1;
TL0=0x20;
TMOD=0X01;
EA=1;
ET0=1;
TR0=1;
}
void Delay5ms() //@12.000MHz
{
unsigned char i, j;
i = 59;
j = 90;
do
{
while (--j);
} while (--i);
}
void Delay1ms() //@12.000MHz
{
unsigned char i, j;
i = 12;
j = 169;
do
{
while (--j);
} while (--i);
}
void Key_Board()
{
unsigned char Temp;
P44=0;P42=1;P3=0X7F;
Temp=P3;
Temp=Temp&0x0F;
if(Temp!=0x0F)
{
Delay5ms();
Temp=P3;
Temp=Temp&0x0F;
if(Temp!=0x0F)
{
Temp=P3;
switch(Temp)
{
case 0x7E:Key_Value=7;break;
case 0x7D:Key_Value=6;break;
case 0x7B:Key_Value=5;break;
case 0x77:Key_Value=4;Key_Press=0;break;
}
while(Temp!=0x0F)
{
Temp=P3;
Temp=Temp&0x0F;
}
Flag=1;
}
}
if(Temp==0x0F&Key_Press==0)//松手检测
{Key_Press=1;}
}
void Key_Dig()
{
if(Flag==1)
{
Flag=0;
if(Key_Value==4)//减
{
if(Temper_Set!=0)//代表是闹钟设置
{
switch(Temper_Set)
{
case 1:Init_Clock[2]--;break;
case 2:Init_Clock[1]--;break;
case 3:Init_Clock[0]--;break;
}
}
if(Time_Set!=0)//代表时间设置
{
switch(Time_Set)
{
case 1:Init_Clock[2]--;break;
case 2:Init_Clock[1]--;break;
case 3:Init_Clock[0]--;break;
}
}
}
if(Key_Value==5)//加
{
if(Temper_Set!=0)//代表是闹钟设置
{
switch(Temper_Set)
{
case 1:Init_Clock[2]++;break;
case 2:Init_Clock[1]++;break;
case 3:Init_Clock[0]++;break;
}
}
if(Time_Set!=0)//代表时间设置
{
switch(Time_Set)
{
case 1:Init_Tab[2]++;break;
case 2:Init_Tab[1]++;break;
case 3:Init_Tab[0]++;break;
}
}
}
if(Key_Value==6)//按下S6时,如果其他设置正在设置,无法完成S6设置,直到另一个设置完成.
{
if(Time_Set==0)
{
if(Status==1){Temper_Set++;}//设置此处主要是用于在时间设置和闹钟设置两设置模式切换后,时间可以正常流动而不是停滞
Status=1;
if(Temper_Set==4){Temper_Set=0;}
if(Temper_Set==0){Shut=0;Time_Gap=1;}
else{Shut=1;}
}
}
if(Key_Value==7)//按下S7时,如果其他设置正在设置,无法完成S7设置,直到另一个设置完成.
{
if(Temper_Set==0)
{
if(Status==0){Time_Set++;}//设置此处主要是用于在时间设置和闹钟设置两设置模式切换后,时间可以正常流动而不是停滞
Status=0;
if(Time_Set==4){Time_Set=0;}
if(Time_Set==0){Shut=0;Time_Gap=1;}
else{Shut=1;}
}
}
}
}
void Clock()
{
if(Init_Tab[0]==Init_Clock[0]&&Init_Tab[1]==Init_Clock[1]&&Init_Tab[2]==Init_Clock[2])//达到定时时间时候
{
Time=500;
}
}
void LED_Light()
{
if(Time_Set!=0|Temper_Set!=0)
{
P2=0X80;P0=0XFF;Time1=0;Time=0;
}
}
void main()
{
All_Init();
Timer0_Init();
while(1)
{
Key_Board();
SMG_LIGHT();
Clock();
Key_Dig();
LED_Light();
}
}
void Timer0() interrupt 1
{
TH0=0XD1;
TL0=0X20;
Time_Count++;
SMG_LIGHT();//数码管函数放在中断使用,避免按下时数码管消失,也可以解决松山检测遇到的BUG。
if(Time_Count==80){Time_Count=0;Temper=Temper_Get();}
if(Shut==1)
{
Time_Gap++;
if(Time_Gap==202){Time_Gap=1;}//闪烁功能
}
if(Shut==0)
{
Count++;
}
if(Count==100)//秒
{
Count=0;
Init_Tab[2]++;
}
if(Time==500)//5S闹钟,
{
Time1++;
if((Time1%20)==0)
{
P2=0X80;P0=~0x01;
}
else
{
P2=0X80;P0=0XFF;
}
if(Time1==500|Flag==1){Time1=0;Time=0;P2=0X80;P0=0XFF;}//按下任意键闹钟提示消失
}
}
DS18B20.c
#include"STC12C5A60S2.h"
sbit DQ=P1^4;
void Delay500us() //@12.000MHz
{
unsigned char i, j;
i = 6;
j = 211;
do
{
while (--j);
} while (--i);
}
void Delay80us() //@12.000MHz
{
unsigned char i, j;
i = 1;
j = 236;
do
{
while (--j);
} while (--i);
}
void DS18B20_Init()//初始化
{
DQ=0;
Delay500us();
DQ=1;
Delay500us();
}
void DS18B20_Write(unsigned char dat)//向DS18B20写入数据
{
unsigned char i;
for(i=0;i<8;i++)
{
DQ=0;
if(dat&0x01)
{DQ=1;}
else
{DQ=0;}
Delay80us();
DQ=1;
dat>>=1;
}
}
unsigned char DS18B20_Read()
{
unsigned char i;
unsigned char dat;
for(i=0;i<8;i++)
{
DQ=0;
dat>>=1;
DQ=1;
if(DQ)
{
dat|=0x80;
}
Delay80us();
}
return dat;
}
long Temper_Get()
{
unsigned char high,low;
long Temp;
DS18B20_Init();
DS18B20_Write(0XCC);
DS18B20_Write(0x44);
DS18B20_Init();
DS18B20_Write(0XCC);
DS18B20_Write(0xBE);
low=DS18B20_Read();
high=DS18B20_Read();
Temp=high&0x0f;
Temp<<=8;
Temp=Temp|low;
Temp=Temp*625;
return Temp;
}
DS18B20.h
#ifndef _DS18B20_H_
#define _DS18B20_H_
long Temper_Get();
unsigned char DS18B20_Read();
void DS18B20_Write(unsigned char dat);
void DS18B20_Init();
#endif
本代码,未设置下限溢出,请自行添加上。