使用了 溫度傳感器 和DS1302時鐘芯片
仿真原理圖如下(proteus仿真工程文件可到本帖附件中下載)
QQ圖片20171219220016.png (63.92 KB, 下載次數: 82)
下載附件
2017-12-19 22:03 上傳
0.png (4.49 KB, 下載次數: 80)
下載附件
2017-12-19 23:05 上傳
單片機源程序如下(注釋部分很詳細):
#include<reg52.h>
#include<intrins.h>
#define uchar unsigned char
#define uint unsigned int
#define LCD1602_DATA P0 //定義P3口為定LCD數據口
sbit buzz=P2^7;
sbit LCD1602_RS=P1^2;
sbit LCD1602_RW=P1^1;
sbit LCD1602_E =P1^0;
sbit key_select=P3^2; //定義選擇按鍵的IO口
sbit key_increment=P3^3; //定義自加按鍵的IO口
sbit key_decrement=P3^4; //定義自減按鍵的IO口
sbit key_detemine= P3^5; //定義確定按鍵的IO口
sbit SCLK=P1^5;
sbit DSIO=P1^6;
sbit RST=P1^7;
sbit DQ=P2^0;//定義DS18B20的數據通訊IO口為P2.4
unsigned char year; //定義變量year, 用來存儲從ds1302時鐘芯片中獲取的年份數據
unsigned char week; //定義變量week, 用來存儲從ds1302時鐘芯片中獲取的星期數據
unsigned char month; //定義變量month, 用來存儲從ds1302時鐘芯片中獲取的月份數據
unsigned char day; //定義變量day, 用來存儲從ds1302時鐘芯片中獲取的日份數據
static unsigned char hour; //定義變量hour, 用來存儲從ds1302時鐘芯片中獲取的小時數據
static unsigned char minute;//定義變量minute, 用來存儲從ds1302時鐘芯片中獲取的分鐘數據
static unsigned char second;//定義變量secode, 用來存儲從ds1302時鐘芯片中獲取的秒鐘數據
unsigned char temperature_integer;//定義變量temperature_integer,用來存儲讀取的溫度整數部分
unsigned char temperature_decimal;//定義變量temperature_decimal,用來存儲讀取溫度的小數部分
unsigned char set_time_state; //當值為1時進入設計時間的循環中,當為0時退出設計時間狀態
unsigned char lcd1602_add; //記錄LCD1602數據指針地址
static unsigned char alarm_hour=7; //存儲鬧鐘小時數據變量
static unsigned char alarm_minute=30; //存儲鬧鐘分鐘數據變量
static unsigned char hour_ten; // 小時的十進制
static unsigned char minute_ten; //分鐘的十進制
uchar ditab[16]= {0,1,1,2,3,3,4,4,5,6,6,7,8,8,9,9}; //小數部分表格,用來計算方法獲取
static unsigned char *Week_dat[]={
"0000",
"Mon ",
"TUes",
"Wed ",
"Thur",
"Fir ",
"Sat ",
"Sun ",
};
unsigned char Temp_L,Temp_H;
/********************************************
函數名稱:delay_ms(uint x)
函數功能:延時一定時間
參數:多少毫秒
************************************************/
void delay(uint x)//延時函數
{
uchar i;
while(x--)
for(i=114; i>0; i--);
}
/*--------------------------------------------------------------------------
函數名稱:Delay7ms()
函數功能:延時7毫秒
輸入參數:無
返回值: 無
特別說明:晶振頻率工作在12MHZ情況下延時7毫秒
--------------------------------------------------------------------------*/
void Delay7ms() //@12.000MHz
{
unsigned char i, j;
i = 82;
j = 179;
do
{
while (--j);
} while (--i);
}
/*--------------------------------------------------------------------------
函數名稱:Delay10us()
函數功能:延時10微秒
輸入參數:無
返回值: 無
特別說明:晶振頻率工作在12MHZ情況下延時7毫秒
--------------------------------------------------------------------------*/
void Delay10us() //@12.000MHz
{
unsigned char i;
_nop_();
i = 2;
while (--i);
}
/*--------------------------------------------------------------------------
函數名稱:Delay50us()
函數功能:延時50微秒
輸入參數:無
返回值: 無
特別說明:晶振頻率工作在12MHZ情況下延時7毫秒
--------------------------------------------------------------------------*/
void Delay50us() //@12.000MHz
{
unsigned char i;
_nop_();
i = 22;
while (--i);
}
/*--------------------------------------------------------------------------
函數名稱:Delay500us()
函數功能:延時500微秒
輸入參數:無
返回值: 無
特別說明:晶振頻率工作在12MHZ情況下延時7毫秒
--------------------------------------------------------------------------*/
void Delay500us() //@12.000MHz
{
unsigned char i;
_nop_();
i = 247;
while (--i);
}
/*--------------------------------------------------------------------------
函數名稱:Delay500ms()
函數功能:延時500毫秒
輸入參數:無
返回值: 無
特別說明:晶振頻率工作在12MHZ情況下延時7毫秒
--------------------------------------------------------------------------*/
void Delay500ms() //@12.000MHz
{
unsigned char i, j, k;
_nop_();
i = 4;
j = 205;
k = 187;
do
{
do
{
while (--k);
} while (--j);
} while (--i);
}
void Delay800ms() //@12.000MHz
{
unsigned char i, j, k;
_nop_();
i = 7;
j = 21;
k = 96;
do
{
do
{
while (--k);
} while (--j);
} while (--i);
}
/****************************************/
/*****************************************
函數名稱:LCD1602_write_com(uchar com)
函數參數:要寫入的指令
函數功能:向lcd1602寫入一個指令
函數返回值:無
*****************************************/
void LCD1602_Write_Com(uchar com)//寫指令
{
LCD1602_E=0;
LCD1602_RS=0;
LCD1602_RW=0;
LCD1602_DATA =com;
LCD1602_E=1;
delay(2);
LCD1602_E=0;
}
/****************************************/
/*****************************************
函數名稱:LCD1602_write_date(uchar dat)
函數參數:要寫入的指令
函數功能:向lcd1602寫入一個指令
函數返回值:無
*****************************************/
void LCD1602_Write_Date(uchar dat)//寫數據
{
LCD1602_E=0;
LCD1602_RS=1;
LCD1602_RW=0;
LCD1602_DATA =dat;
LCD1602_E=1;
delay(2);
LCD1602_E=0;
}
/******************************************
函數名稱:LCD1608_Init()
函數參數:無
函數功能:初始化LCD1602
函數返回值:無
*********************************************/
void LCD1602_Init()//初始化LCD_1602
{
delay(15);
LCD1602_Write_Com(0X38);
delay(5);
LCD1602_Write_Com(0X38);
delay(5);
LCD1602_Write_Com(0X38);
LCD1602_Write_Com(0X38);
LCD1602_Write_Com(0X01);
LCD1602_Write_Com(0X06);
LCD1602_Write_Com(0X0c);
}
/******************************************************
函數: void LCD1602_printf(uchar H,uchar L,uchar dat)
函數參數:H表示行,L表示列,dat表示數據
函數功能:在指定的H行,第L+1個處開始寫入一個字符
函數返回值:無
*******************************************************/
void LCD1602_Printf(bit H,uchar L,uchar dat)
{
if(H)
{
LCD1602_Write_Com(0X80+0X40+L);
LCD1602_Write_Date(dat);
}
else
{
LCD1602_Write_Com(0X80+L);
LCD1602_Write_Date(dat);
}
}
/*********************************************************
函數名稱:LCD1602_ClS()
函數功能:清楚屏幕
函數參數:無
函數返回值:無
**********************************************************/
void LCD1602_Cls()
{
LCD1602_Write_Com(0x01);
}
/*********************************************************
函數名稱:void LCD1602_Printf_String(bit H,uchar L,uchar dat)
函數功能:H表示行,L表示列,dat表示數據
函數參數:無
函數返回值:無
**********************************************************/
void LCD1602_Printf_String(bit H,uchar L,uchar* str)
{
if(H)
{
LCD1602_Write_Com(0X80+0X40+L);
while(*str!='\0')
{
LCD1602_Write_Date(*str++);
}
}
else
{
LCD1602_Write_Com(0X80+L);
while(*str!='\0')
{
LCD1602_Write_Date(*str++);
}
}
}
/*--------------------------------------------------------------------------
函數名稱:bit Key_Select_Is_Dowm()
函數功能:檢測key_select按鍵是否被按下,按鍵被按下返回1,按鍵沒有被按下返回0
輸入參數:無。
返回值:按鍵被按下返回1,按鍵沒有被按下返回0
--------------------------------------------------------------------------*/
bit Key_Select_Is_Dowm()
{
if(!key_select)
{
Delay7ms();
if(!key_select)
{
return 1;
}
}
return 0;
}
/*--------------------------------------------------------------------------
函數名稱:bit Key_Increment_Is_Dowm()
函數功能:檢測key_increment按鍵是否被按下,按下返回1,沒有被按下返回0
輸入參數:無
返回值: 按鍵被按下返回1,按鍵沒有被按下返回0
--------------------------------------------------------------------------*/
bit Key_Increment_Is_Dowm()
{
if(!key_increment)
{
Delay7ms();
if(!key_increment)
{
return 1;
}
}
return 0;
}
/*--------------------------------------------------------------------------
函數名稱:bit Key_Decrement_Is_Dowm()
函數功能:檢測key_decrement按鍵是否被按下,按下返回1,沒有被按下返回0
輸入參數:無
返回值: 按鍵被按下返回1,按鍵沒有被按下返回0
--------------------------------------------------------------------------*/
bit Key_Decrement_Is_Dowm()
{
if(!key_decrement)
{
Delay7ms();
if(!key_decrement)
{
return 1;
}
}
return 0;
}
/*--------------------------------------------------------------------------
函數名稱:bit Key_determine_Is_Dowm()
函數功能:檢測key_determine按鍵是否被按下,按下返回1,沒有被按下返回0
輸入參數:無
返回值: 按鍵被按下返回1,按鍵沒有被按下返回0
--------------------------------------------------------------------------*/
bit Key_Determine_Is_Dowm()
{
if(!key_detemine)
{
Delay7ms();
if(!key_detemine)
{
return 1;
}
}
return 0;
}
/*--------------------------------------------------------------------------
函數名稱:void write_ds1302(uchar dat)
函數功能:向DS1302芯片寫入一個字節
輸入參數:寫入的數據
返回值:無
--------------------------------------------------------------------------*/
void Ds1302_Write(uchar dat)//寫入一個字節
{
uchar i;
for(i=0; i<8; i++)
{
DSIO=dat&0x01;
SCLK=1;
dat>>=1;
SCLK=0;
}
}
/*--------------------------------------------------------------------------
函數名稱: read_ds1302())
函數功能:向DS1302芯片讀取一個字節
輸入參數:無
返回值: 返回DS_1302讀取的一個數據
--------------------------------------------------------------------------*/
uchar Ds1302_Read()//讀出一個字節
{
uchar i,tem=0;
for(i=0; i<8; i++)
{
tem>>=1;
if(DSIO)
tem|=0x80;
SCLK=1;
SCLK=0;
}
return tem;
}
/*--------------------------------------------------------------------------
函數名稱: rest_ds1302()
函數功能:ds1302復位
輸入參數:無
返回值:
--------------------------------------------------------------------------*/
void Ds1302_Rest()//ds1302復位
{
RST=0;
DSIO=0;
RST=1;
}
/*--------------------------------------------------------------------------
函數名稱:write(uchar add,uchar addr)
函數功能:向DS1302寫入一個數據
輸入參數:地址,數據
返回值: 無
--------------------------------------------------------------------------*/
void Ds1302_Write_Data(uchar add,uchar dat)//寫入一個數據
{
uchar t;
t=dat/10;
dat=dat%10;
dat=t*16+dat; //轉化為BCD碼
Ds1302_Rest();
Ds1302_Write(add);
Ds1302_Write(dat);
RST=0;
DSIO=0;
}
/*--------------------------------------------------------------------------
函數名稱:write_BCD(uchar add,uchar addr)
函數功能:向DS1302寫入一個BCD數據
輸入參數:地址,數據
返回值: 無
--------------------------------------------------------------------------*/
void DS1302_Write_BCD(uchar add,uchar dat)//寫入一個BCD數據
{
// uchar t;
// t=dat/10;
// dat=dat%10;
// dat=t*16+dat; //轉化為BCD碼
Ds1302_Rest();
Ds1302_Write(add);
Ds1302_Write(dat);
RST=0;
DSIO=0;
}
/*--------------------------------------------------------------------------
函數名稱:read(uchar add)
函數功能:讀出一個時間
輸入參數:地址
返回值: 時間
--------------------------------------------------------------------------*/
uchar Ds1302_Read_Time(uchar add)//讀出一個時間
{
uchar temp;
Ds1302_Rest();
Ds1302_Write(add);
temp=Ds1302_Read();
RST=0;
DSIO=0;
return temp;
}
/*--------------------------------------------------------------------------
函數名稱:Open_Wp()
函數功能:打開寫保護開關,失之不可以對DS1302進行寫操作
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Ds1302_Open_Wp()
{
Ds1302_Write_Data(0x8e,0x80);
}
/*--------------------------------------------------------------------------
函數名稱:Colse_Wp()
函數功能:關閉寫保護開關,使之可以對DS1302進行寫操作
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Ds1302_Close_Wp()
{
Ds1302_Write_Data(0x8e,0);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Year_BCD()
函數功能:獲取DS1302內部年份寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Year_BCD()
{
return Ds1302_Read_Time(0x8d);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Week_BCD()
函數功能:獲取DS1302內部星期寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Week_BCD()
{
return Ds1302_Read_Time(0x8B);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Month_BCD()
函數功能:獲取DS1302內部月份寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Month_BCD()
{
return Ds1302_Read_Time(0x89);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Day_BCD()
函數功能:獲取DS1302內部日份占拇嫫魘藎ɑ袢〉鼻靶∈筆藎?
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Day_BCD()
{
return Ds1302_Read_Time(0x87);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Hour_BCD()
函數功能:獲取DS1302內部小時寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Hour_BCD()
{
return Ds1302_Read_Time(0x85);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Minute _BCD()
函數功能:獲取DS1302內部小時寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Minute_BCD()
{
return Ds1302_Read_Time(0x83);
}
/*--------------------------------------------------------------------------
函數名稱:uchar Get_Ds1302_Second_BCD()
函數功能:獲取DS1302內部小時寄存器數據(獲取當前小時數據)
輸入參數:無
返回值: 當前DS1302芯片內部存儲小時,數值為BCD碼
--------------------------------------------------------------------------*/
uchar Get_Ds1302_Second_BCD()
{
return Ds1302_Read_Time(0x81);
}
/********************************************************************************************** //
函數名稱:Ds18b20_Init() //
函數功能:DS18B20初始化 //
輸入參數:無 //
返回值:返回為1表示DS18B20發出了存在信息,為0表示沒有? // //
************************************************************************************************/
uchar Ds18b20_Init() //
{ //
uchar value; //定義一個變量value,用來保存中間結果。 //
DQ=1; //把總線拉為高電平。 //
Delay10us(); //保持10us,目的是為了穩定系統端口。 //
DQ=0; //初始化第一步,總線拉為低電平,低電平時間應該保持480us-960us之間。 //
Delay500us(); //這里選擇保持500us。 //
DQ=1; //初始化第二步:總線拉為高電平(釋放端口),用于下一步檢測DS18B20 //
Delay50us(); //延時50微妙。 //
value=DQ; //檢測總線電平,并把值賦給變量value,返回為1表示DS18B20發出了存在信息, //
//為0表示沒有發出存在信息 //
Delay500us(); //檢測 總線電平后延時500us,為了穩定系統總線。
Delay50us(); //延時50微妙。 //
return value; //返回value值 //
} //
/***********************************************************************************************/
/*******************************************************************************************
函數名稱: Ds18b20_Write_Date(uchar dat)
函數功能:向DS18B20中寫入一個數據
輸入參數:要寫入數據的值
返回值:無
*******************************************************************************************/
void Ds18b20_Write_Date(uchar dat)
{
uchar i; //定義局部變量i,用于循環計數
for(i=0; i<8; i++) //循環8次將寫入一個8位的數據
{
DQ=1; //把總線拉為高電平
Delay10us(); //保持10us,目的是為穩定系統端口。
DQ=0; //總線時間為低電平,保持時間大于1us后寫數據。
_nop_(); //空操作,延時1us。
DQ=dat&0x01; //向DS18b20中寫入一位數據。
dat>>=1; //數據右移一位準備寫入下一位,DS18B20先寫低位再寫高位。
Delay50us(); //延時50us
Delay10us(); //延時10us,為了DS18b20 采樣總線上的數據
DQ=1;
// Delay10us(); //延時10us,為了DS18b20 采樣總線上的數據
}
DQ=1; //釋放總線。
}
/*****************************************************************************
函數名稱:uchar Ds18b20_Read_Date()
函數功能:從DS18B20中讀取一個字節數據
輸入參數:無
返回值:讀取到的值
******************************************************************************/
uchar Ds18b20_Read_Date()
{
uchar i, value;//定義中間變量
for(i=0; i<8; i++)
{
DQ=1; //將總線拉為高電平
Delay10us(); //保持10us,目的是為了讓系統端口穩定。
DQ=0; //把總線拉為低電平。
_nop_();
_nop_();
value>>=1; //1,延時,2,數據右移一位,準備讀下一位
DQ=1; //把總線拉為高電平準備讀數據
_nop_();
_nop_();
if(DQ)
{
value|=0x80;
}
Delay50us(); //延時50us
DQ=1; //釋放總線
}
return value; //返回讀取到的字節數據
}
/*****************************************************************************
函數名稱:uchar Get_Ds18b20_Temperature(bit Va
函數功能:讀取溫度程序
輸入參數:輸入參數為0返回溫度的小數,輸入參數為1則返回溫度的整數
返回值:讀取到的值
******************************************************************************/
uchar Get_Ds18b20_Temperature_Integer()//讀取溫度程序,參數為1,返回整數,參數為小數
{
unsigned char temp_integer;
while(Ds18b20_Init()); //初始化DS18B20。
Ds18b20_Write_Date(0xcc); //跳過ROM命令。
_nop_();
Ds18b20_Write_Date(0x44); //啟動溫度轉換。
// Delay500ms();
while(!DQ); //等待轉化完畢
while(Ds18b20_Init()); //初始化DS18B20。
Ds18b20_Write_Date(0xcc); //跳過ROM命令。
_nop_();
Ds18b20_Write_Date(0xbe); //啟動溫度轉換。
Temp_L=Ds18b20_Read_Date(); //讀取到溫度的低字節。
Temp_H=Ds18b20_Read_Date(); //暫存讀取到的溫度低字節。
temp_integer=(Temp_H<<4)+(Temp_L>>4);
return temp_integer; //返回溫度的整數部分
}
/*****************************************************************************
函數名稱:uchar Get_Ds18b20_Decimal
函數功能:讀取溫度程序的小數部分
輸入參數:無
返回值:讀取到的溫度的小數的值
******************************************************************************/
uchar Get_Ds18b20_Temperature_Decimal()//讀取溫度程序,參數為1,返回整數,參數為小數
{
unsigned char temp_decimal;
if(Temp_H&0x80)
{
Temp_L=~Temp_L;
}
temp_decimal=ditab[Temp_L&0x0f];
return temp_decimal;
}
/*--------------------------------------------------------------------------
函數名稱:void Update_Time()
函數功能:更新,年,周,月,日,小時,分鐘,秒鐘的變量里的數據
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Update_Time()
{
year = Get_Ds1302_Year_BCD(); //更新年份數據
week = Get_Ds1302_Week_BCD(); //更新周數據
month = Get_Ds1302_Month_BCD(); //更新月份數據
day = Get_Ds1302_Day_BCD(); //更新日期數據
hour = Get_Ds1302_Hour_BCD(); //更新小時數據
minute= Get_Ds1302_Minute_BCD();//更新月份數據
second= Get_Ds1302_Second_BCD(); //更新秒種數據
}
/*--------------------------------------------------------------------------
函數名稱:void Update_Time()
函數功能:更新,年,周,月,日,小時,分鐘,秒鐘的變量里的數據
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
//void Update_Temperature()
//{
// // temperature_integer=Get_Ds18b20_Temperature(1);
// //temperature_decimal=Get_Ds18b20_Temperature(0);
//}
/*--------------------------------------------------------------------------
函數名稱:void Update_Time()
函數功能:更新,年,周,月,日,小時,分鐘,秒鐘的變量里的數據
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Dispaly_Temperature()
{
temperature_integer=Get_Ds18b20_Temperature_Integer();
temperature_decimal=Get_Ds18b20_Temperature_Decimal();
if(temperature_integer<127)
{
LCD1602_Printf(1,10,'+');
}
else
{
temperature_integer=~temperature_integer;
LCD1602_Printf(1,10,'-');
}
LCD1602_Printf(1,11,(temperature_integer/10)+48);
LCD1602_Printf(1,12,(temperature_integer%10)+48);
LCD1602_Write_Date('.');
LCD1602_Printf(1,14,(temperature_decimal)+48);
LCD1602_Write_Date('C');
}
/*--------------------------------------------------------------------------
函數名稱:Dispaly_Time()
函數功能:更新顯示年,周,月,日,小時,分鐘,秒鐘
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Dispaly_Time()
{
//LCD1602_Cls();
LCD1602_Printf_String(0,0,"20");
LCD1602_Printf(0,2,(year>>4)+48); //year變量的高四位存儲年份的十位,取year的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,3,(year&0x0f)+48); //year變量的低四位存儲年份的個位,取year的低四位,+48就轉換為對應數字的字符
LCD1602_Write_Date('/');
LCD1602_Printf(0,5,(month>>4)+48); //month變量的高四位存儲月份的十位,取month的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,6,(month&0x0f)+48); //month變量的低四位存儲月份的個位,取month的低四位,+48就轉換為對應數字的字符
LCD1602_Write_Date('/');
LCD1602_Printf(0,8,(day>>4)+48); //day變量的高四位存儲日份的十位,取day的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,9,(day&0x0f)+48); //day變量的低四位存儲日份的個位,取day的低四位,+48就轉換為對應數字的字符
LCD1602_Printf_String(0,12,Week_dat[week&0x0f]); // 調用week_dat數組內對應數據
// LCD1602_Printf(0,12,(week>>4)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
// LCD1602_Printf(0,13,(week&0x0f)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
// LCD1602_Printf_String(0,14,"th");
LCD1602_Printf(1,1,(hour>>4)+48); //hour變量的高四位存儲小時的十位,取hour的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,2,(hour&0x0f)+48); //hour變量的低四位存儲小時的個位,取hour的低四位,+48就轉換為對應數字的字符
LCD1602_Write_Date(':');
LCD1602_Printf(1,4,(minute>>4)+48); //minute變量的高四位存儲分鐘的十位,取minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,5,(minute&0x0f)+48); //minute變量的低四位存儲分鐘的個位,取minute的高四位,+48就轉換為對應數字的字符
LCD1602_Write_Date(':');
LCD1602_Printf(1,7,(second>>4)+48); //second變量的高四位存儲秒鐘的十位,取second的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,8,(second&0x0f)+48); //second變量的高四位存儲秒鐘的個位,取second的高四位,+48就轉換為對應數字的字符
year=(year>>4)*10+(year&0x0f);
month=(month>>4)*10+(month&0x0f);
day=(day>>4)*10+(day&0x0f); //由BCD碼轉變為十進制碼
week=week&0x0f;
hour=(hour>>4)*10+(hour&0x0f);
minute=(minute>>4)*10+(minute&0x0f);
second=(second>>4)*10+(second&0x0f);
if((alarm_hour==hour)&&(alarm_minute==minute)) //鬧鐘檢測
{
if(second%2)
{
buzz=0;
}
else
{
buzz=1;
}
}
else
{
buzz=1;
}
while(minute==0&&second==0) //整點報時
{
if(minute==0&&second==0)
{
buzz=0;
}
else
{
buzz=1;
}
Update_Time();
}
}
/*--------------------------------------------------------------------------
函數名稱: Set_Time()
函數功能:調整設置時間
輸入參數:無
返回值: 無
--------------------------------------------------------------------------*/
void Set_Time()
{
if(Key_Select_Is_Dowm())
{
buzz=0;
set_time_state=1;
lcd1602_add=0x83;
LCD1602_Write_Com(0x0f);//開顯示光標,并且光標閃爍
while(Key_Select_Is_Dowm());
buzz=1;
}
while(set_time_state)
{
LCD1602_Write_Com(lcd1602_add);
if(Key_Select_Is_Dowm())
{
buzz=0;
switch(lcd1602_add)
{
case 0x83 :
lcd1602_add=0x86;
break;
case 0x86 :
lcd1602_add=0x89;
break;
case 0x89 :
lcd1602_add=0x8d;
break;
case 0x8d :
lcd1602_add=0xc2;
break;
case 0xc2 :
lcd1602_add=0xc5;
break;
case 0xc5 :
lcd1602_add=0xc8;
break;
case 0xc8 :
lcd1602_add=0x83;
break;
default :
break;
}
while(Key_Select_Is_Dowm());
buzz=1;
}
if(Key_Increment_Is_Dowm())
{
buzz=0;
switch(lcd1602_add)
{
case 0x83:
year++;
if(year>99)
{
year=0;
}
LCD1602_Printf(0,2,(year/10)+48); //year變量的高四位存儲年份的十位,取year的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,3,(year%10)+48); //year變量的低四位存儲年份的個位,取year的低四位,+48就轉換為對應數字的字符
break;
case 0x86:
month++;
if(month>12)
{
month=1;
}
LCD1602_Printf(0,5,(month/10)+48); //year變量的高四位存儲年份的十位,取year的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,6,(month%10)+48); //year變量的低四位存儲年份的個位,取year的低四位,+48就轉換為對應數字的字符
break;
case 0x89:
day++;
switch(month)
{
case 1:
case 3:
case 5:
case 7:
case 8:
case 10:
case 12:
if(day>31)
{
day=1;
}
break;
case 4:
case 6:
case 9:
case 11:
if(day>30)
{
day=1;
}
break;
case 2:
if(year%4==0)
{
if(day>29)
{
day=1;;
}
break;
}
if(day>28)
{
day=1;
}
break;
default :
break;
}
LCD1602_Printf(0,8,(day/10)+48); //month變量的高四位存儲月份的十位,取month的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,9,(day%10)+48); //month變量的低四位存儲月份的個位,取month的低四位,+48就轉換為對應數字的字符
break;
case 0x8d:
week++;
if(week>7)
{
week=1;
}
LCD1602_Printf_String(0,12,Week_dat[week&0x0f]); // 調用week_dat數組內對應數據
// LCD1602_Printf(0,12,(week/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
// LCD1602_Printf(0,13,(week%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
break;
case 0xc2:
hour++;
if(hour>23)
{
hour=0;
}
LCD1602_Printf(1,1,(hour/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,2,(hour%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
break;
case 0xc5:
minute++;
if(minute>59)
{
minute=0;
}
LCD1602_Printf(1,4,(minute/10)+48); //minute變量的高四位存儲分鐘的十位,取minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,5,(minute%10)+48); //minute變量的低四位存儲分鐘的個位,取minute的高四位,+48就轉換為對應數字的字符
break;
case 0xc8:
second++;
if(second>59)
{
second=0;
}
LCD1602_Printf(1,7,(second/10)+48); //second變量的高四位存儲秒鐘的十位,取second的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,8,(second%10)+48); //second變量的高四位存儲秒鐘的個位,取second的高四位,+48就轉換為對應數字的字符
break;
default :
break;
}
while(Key_Increment_Is_Dowm());
buzz=1;
}
//自減按鍵
if(Key_Decrement_Is_Dowm())
{
buzz=0;
switch(lcd1602_add)
{
case 0x83:
if(year>0)
{
year--;
}
else
{
year=99;
}
LCD1602_Printf(0,2,(year/10)+48); //year變量的高四位存儲年份的十位,取year的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,3,(year%10)+48); //year變量的低四位存儲年份的個位,取year的低四位,+48就轉換為對應數字的字符
break;
case 0x86:
if(month>1)
{
month--;
}
else
{
month=12;
}
LCD1602_Printf(0,5,(month/10)+48); //year變量的高四位存儲年份的十位,取year的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,6,(month%10)+48); //year變量的低四位存儲年份的個位,取year的低四位,+48就轉換為對應數字的字符
break;
case 0x89:
switch(month)
{
case 1:
case 3:
case 5:
case 7:
case 8:
case 10:
case 12:
if(day>1)
{
day--;
}
else
{
day=31;
}
break;
case 4:
case 6:
case 9:
case 11:
if(day>1)
{
day--;
}
else
{
day=30;
}
break;
break;
case 2:
if(year%4==0)
{
if(day>1)
{
day--;
}
else
{
day=29;
}
break;
}
else
{
if(day>1)
{
day--;
}
else
{
day=28;
}
}
break;
default :
break;
}
LCD1602_Printf(0,8,(day/10)+48); //month變量的高四位存儲月份的十位,取month的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,9,(day%10)+48); //month變量的低四位存儲月份的個位,取month的低四位,+48就轉換為對應數字的字符
break;
case 0x8d:
if(week>1)
{
week--;
}
else
{
week=7;
}
LCD1602_Printf(0,12,(week/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(0,13,(week%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
break;
case 0xc2:
if(hour>0)
{
hour--;
}
else
{
hour=23;
}
LCD1602_Printf(1,1,(hour/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,2,(hour%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
break;
case 0xc5:
if(minute>0)
{
minute--;
}
else
{
minute=59;
}
LCD1602_Printf(1,4,(minute/10)+48); //minute變量的高四位存儲分鐘的十位,取minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,5,(minute%10)+48); //minute變量的低四位存儲分鐘的個位,取minute的高四位,+48就轉換為對應數字的字符
break;
case 0xc8:
if(second>0)
{
second--;
}
else
{
second=59;
}
LCD1602_Printf(1,7,(second/10)+48); //second變量的高四位存儲秒鐘的十位,取second的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,8,(second%10)+48); //second變量的高四位存儲秒鐘的個位,取second的高四位,+48就轉換為對應數字的字符
break;
default :
break;
}
while(Key_Decrement_Is_Dowm());
buzz=1;
}
if(Key_Determine_Is_Dowm())
{
buzz=0;
set_time_state=0; //設置完成,退出循環
LCD1602_Write_Com(0x0c);//關閉光標
Ds1302_Close_Wp();//關閉DS1302寫保護,使之可以對其進行寫操作
Ds1302_Write_Data(0x8c,year);
Ds1302_Write_Data(0x88,month);
Ds1302_Write_Data(0x8a,week);
Ds1302_Write_Data(0x86,day);
Ds1302_Write_Data(0x84,hour);
Ds1302_Write_Data(0x82,minute);
Ds1302_Write_Data(0x80,second);
Ds1302_Open_Wp();//打開ds1302寫保護,使之不可以對其進行寫操作
while(Key_Determine_Is_Dowm());
buzz=1;
break;
}
}
}
/************************************************
函數名稱: set_alarm()
函數功能:設計鬧鐘時間
輸入參數:無
返回值: 無
*********************************************/
void set_alarm()
{
LCD1602_Cls(); //清除屏幕
LCD1602_Printf_String(0,1,"alarm clock ");
LCD1602_Printf(1,1,(alarm_hour/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,2,(alarm_hour%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,3,':');
LCD1602_Printf(1,4,(alarm_minute/10)+48); //alarm_minute變量的高四位存儲分鐘的十位,取alarm_minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,5,(alarm_minute%10)+48); //alarm_minute變量的低四位存儲分鐘的個位,取alarm_minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,6,':');
LCD1602_Printf(1,7,0+48); //second變量的高四位存儲秒鐘的十位,取second的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,8,0+48); //second變量的高四位存儲秒鐘的個位,取second的高四位,+48就轉換為對應數字的字符
lcd1602_add=0xc2; //光標初始化地址
LCD1602_Write_Com(0x0f);//開顯示光標,并且光標閃爍
set_time_state=1; //菜單標志位置1
while(set_time_state)
{
LCD1602_Write_Com(lcd1602_add); //光標顯示地址
if(Key_Select_Is_Dowm())
{
buzz=0; //蜂鳴器打開
switch(lcd1602_add)
{
case 0xc2 :
lcd1602_add=0xc5;
break;
case 0xc5 :
lcd1602_add=0xc2;
break;
default :
break;
}
while(Key_Select_Is_Dowm());
buzz=1;
}
if(Key_Increment_Is_Dowm())
{
buzz=0;
switch(lcd1602_add)
{
case 0xc2:
alarm_hour++;
if(alarm_hour>23)
{
alarm_hour=0;
}
LCD1602_Printf(1,1,(alarm_hour/10)+48); //week變量的高四位存儲周份的十位,取week的低四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,2,(alarm_hour%10)+48); //week變量的低四位存儲周份的個位,取week的低四位,+48就轉換為對應數字的字符
break;
case 0xc5:
alarm_minute++;
if(alarm_minute>59)
{
alarm_minute=0;
}
LCD1602_Printf(1,4,(alarm_minute/10)+48); //alarm_minute變量的高四位存儲分鐘的十位,取alarm_minute的高四位,+48就轉換為對應數字的字符
LCD1602_Printf(1,5,(alarm_minute%10)+48); //alarm_minute變量的低四位存儲分鐘的個位,取alarm_minute的高四位,+48就轉換為對應數字的字符
break;
default :
break;
}
while(Key_Increment_Is_Dowm());
buzz=1;
}
//自減按鍵
if(Key_Decrement_Is_Dowm())
……………………
…………限于本文篇幅 余下代碼請從51黑下載附件…………
全部資料51hei下載地址:
LCD時鐘.zip
(186.69 KB, 下載次數: 156)
2017-12-19 22:04 上傳
點擊文件名下載附件
下載積分: 黑幣 -5
|