• 方案介紹
    • 一、前言
    • 二、代碼實現(xiàn)
  • 附件下載
  • 相關推薦
申請入駐 產業(yè)圖譜

DS1302實時時鐘芯片_讀寫時間實現(xiàn)電子鐘功能

06/13 10:14
906
加入交流群
掃碼加入
獲取工程師必備禮包
參與熱點資訊討論

更多詳細資料請聯(lián)系.docx

共1個文件

一、前言

1.1 功能說明

本項目以STC90C51單片機為核心,結合DS1302實時時鐘芯片和IIC協(xié)議的OLED顯示屏,設計了一款功能豐富、操作簡便的電子時鐘。

【1】項目目標

  1. 實現(xiàn)高精度的時間顯示,包括時、分、秒。
  2. 提供按鍵調整時間的功能,方便用戶校準時間。
  3. 利用OLED顯示屏以直觀的方式展示時間信息。

【2】系統(tǒng)架構

  1. 微控制器:采用STC90C51單片機作為核心控制器,負責整個系統(tǒng)的數(shù)據處理和邏輯控制。
  2. 實時時鐘芯片:選用DS1302作為實時時鐘芯片,提供高精度的時間信息。DS1302通過I2C接口與STC90C51進行通信,實現(xiàn)時間的讀取和設置。
  3. 顯示屏:采用IIC協(xié)議的OLED顯示屏作為顯示設備,用于顯示時間信息。顯示屏與STC90C51通過SPI I2C接口連接,實現(xiàn)數(shù)據的傳輸和顯示。
  4. 按鍵模塊:設計一組按鍵用于調整時間。按鍵模塊通過GPIO接口與STC90C51連接,實現(xiàn)按鍵信號的輸入和識別。

【3】功能實現(xiàn)

  1. 時間顯示:STC90C51定時從DS1302讀取時間信息,并通過OLED顯示屏進行顯示。顯示屏可以實時更新時間,保證時間的準確性。
  2. 時間調整:用戶通過按鍵模塊輸入調整時間的指令,STC90C51根據指令對DS1302進行設置,實現(xiàn)時間的校準。

1.2 DS1302介紹

DS1302是由美國DALLAS公司推出的一款低功耗實時時鐘芯片,具有涓細電流充電能力。以下是對DS1302的詳細介紹:

【1】主要功能特點

  1. 計時功能:DS1302能夠對年、月、日、周、時、分、秒進行精確計時,并具備閏年補償功能,確保時間的準確性。
  2. 低功耗:該芯片功耗極低,工作電壓在2.0V至5.5V范圍內,使得它非常適合在需要長時間運行且電源有限的設備中使用。
  3. 數(shù)據存儲:DS1302內部具有一個31×8的RAM寄存器,可用于臨時性存放數(shù)據。
  4. 雙電源引腳:DS1302擁有主電源/后備電源雙電源引腳設計,可以在主電源關閉的情況下,通過后備電源保持時鐘的連續(xù)運行。
  5. 串行I/O通信:采用串行I/O通信方式,相對于并行通信更節(jié)省IO口的使用。

【2】引腳說明

DS1302共有8個引腳,包括:

  • VCC2:主電源正極的引腳。
  • X1和X2晶振輸入和輸出引腳,外接32.768kHz晶振。
  • GND:負極。
  • CE:使能引腳,接單片機的IO口,用于啟動和停止時鐘芯片的工作。
  • I/O數(shù)據傳輸引腳,接單片機的IO口,用于數(shù)據的讀寫。
  • SCLK:通信時鐘引腳,接單片機的IO口,用于同步數(shù)據傳輸。
  • RST:復位/片選線,通過把RST輸入驅動置高電平來啟動所有的數(shù)據傳送。RST也有兩種功能:一是接通控制邏輯,允許地址/命令序列送入移位寄存器;二是提供終止單字節(jié)或多字節(jié)數(shù)據傳送的方法。
  • VCC1:后備電源引腳,在主電源關閉時,為DS1302提供電源。

【3】應用領域

由于其穩(wěn)定可靠、易于使用和低功耗等特點,DS1302被廣泛應用于各個領域,包括:

  • 電子產品:如手機、平板電腦等需要準確顯示時間的設備中。
  • 工業(yè)控制系統(tǒng):如自動化生產線、儀器儀表等需要同步計時和記錄數(shù)據的設備中。
  • 汽車電子系統(tǒng):如車載導航儀、車載音響等需要準確顯示時間和日期信息的設備中。

image-20240612113752914

image-20240612113806768

二、代碼實現(xiàn)

2.1 main.c

#include <reg51.h>
#include "delay.h"
#include "type.h"
#include "uart.h"
#include "ds1302.h"
//#include "key.h"
//#include "led.h"
//#include "timer.h"
//#include "exti.h"
//#include "infrared.h"
//#include "ds18b20.h"
//#include "at24c02.h"

int main()
{
    u8 stat;
    UART_Init();        //初始化串口波特率為4800
    DS1302_Init();
    
    stat=DS1302_ReadByte(0x80|0x01);//讀取秒
    if(stat&0x80)
    {
        DS1302_WriteTime(2020-2000,1,18,16,33,33,6);
    }
    else
    {
        printf("DS1302 OKrn");
    }
    
    while(1)
    {
        DS1302_ReadTime();
        printf("DS1302:%d-%d-%d %d:%d:%d %drn",
        (int)DS1302_TIME[0]+2000,
        (int)DS1302_TIME[1],
        (int)DS1302_TIME[2],
        (int)DS1302_TIME[3],
        (int)DS1302_TIME[4],
        (int)DS1302_TIME[5],
        (int)DS1302_TIME[6]
        );     
        DelayMs(1000);
    }
}


2.2 DS1302.c

#include"ds1302.h"
//定義ds1302使用的IO口
sbit DS1302_IO=P3^4;
sbit DS1302_RST=P3^5;
sbit DS1302_SCLK=P3^6;

u8 DS1302_TIME[7]; //存放讀取的時間

/*
函數(shù)功能: 將十進制數(shù)據轉為BCD碼
*/
u8 DEC_TO_BCD(u8 val)
{
	return ((val/10)<<4)+val%10;
}

/*
函數(shù)功能: 將BCD碼數(shù)據轉為十進制格式
*/
u8 BCD_TO_DEC(u8 val)
{
	return (val&0x0f)+(val>>4)*10;
}

void DS1302_Init(void)
{
   DS1302_RST=0;
   DS1302_SCLK=0;//先將DS1302_SCLK置低電平。
}

/*
函數(shù)功能: 向DS1302指定寄存器里寫一個字節(jié)數(shù)據
*/
void DS1302_WriteByte(u8 addr,u8 dat)
{
	u8 n;
	DS1302_RST=1; //然后將DS1302_RST(CE)置高電平。
    /*1. 設置寫入的地址*/
	for(n=0;n<8;n++)
	{
		DS1302_IO=addr&0x01;//數(shù)據從低位開始傳送
		addr>>=1;
		DS1302_SCLK=1;//數(shù)據在上升沿時,DS1302讀取數(shù)據
		DS1302_SCLK=0;
	}
    
    /*2. 寫入數(shù)據*/
	for(n=0;n<8;n++)
	{
		DS1302_IO=dat&0x01;
		dat>>=1;
		DS1302_SCLK=1;//數(shù)據在上升沿時,DS1302讀取數(shù)據
		DS1302_SCLK=0;
	}	
	DS1302_RST=0;//傳送數(shù)據結束
}

/*
函數(shù)功能: 從DS1302指定寄存器里讀取一個字節(jié)數(shù)據
*/
u8 DS1302_ReadByte(u8 addr)
{
	u8 n=0,dat=0;
	DS1302_RST=1;   //然后將DS1302_RST(CE)置高電平。
    /*1. 設置讀取的地址*/
	for(n=0;n<8;n++)
	{
		DS1302_IO=addr&0x01;//數(shù)據從低位開始傳送
		addr>>=1;
		DS1302_SCLK=1;//數(shù)據在上升沿時,DS1302讀取數(shù)據
		DS1302_SCLK=0;//DS1302下降沿時,放置數(shù)據
	}
    /*2. 讀取數(shù)據*/
	for(n=0;n<8;n++)
	{
        dat>>=1;
        if(DS1302_IO)dat|=0x80;
		DS1302_SCLK=1;
		DS1302_SCLK=0;//DS1302下降沿時,放置數(shù)據
	}
	DS1302_RST=0;
    //必須的操作,復位時間
	DS1302_IO=0;
	DS1302_IO=1;
	return dat;	
}

/*
函數(shù)功能: 設置DS1302芯片的時間
DS1302的時間基準是從2000年開始的,設置年份時要減去2000再傳入設置
例如:DS1302_WriteTime(20,1,18,14,46,20,6);
*/
void DS1302_WriteTime(u8 year,u8 mon,u8 mday,u8 hour,u8 min,u8 sec,u8 week)
{
	DS1302_WriteByte(0x8E,0x00); //禁止寫保護,就是關閉寫保護功能	
    DS1302_WriteByte(0x8c,DEC_TO_BCD(year)); //設置年	
    DS1302_WriteByte(0x88,DEC_TO_BCD(mon));  //設置月	
    DS1302_WriteByte(0x86,DEC_TO_BCD(mday)); //設置日	
    DS1302_WriteByte(0x84,DEC_TO_BCD(hour)); //設置時	
    DS1302_WriteByte(0x82,DEC_TO_BCD(min));  //設置分	
    DS1302_WriteByte(0x80,DEC_TO_BCD(sec));  //設置秒	
    DS1302_WriteByte(0x8a,DEC_TO_BCD(week)); //設置星期	
	DS1302_WriteByte(0x8E,0x80);		     //打開寫保護功能
}

/*
函數(shù)功能: 讀取DS1302時鐘的時間
DS1302寄存器的最低位是讀寫位,0是寫,1是讀
*/
void DS1302_ReadTime(void)
{
    DS1302_TIME[0]=BCD_TO_DEC(DS1302_ReadByte(0x8c|0x01));//讀取年
    DS1302_TIME[1]=BCD_TO_DEC(DS1302_ReadByte(0x88|0x01));//讀取月
    DS1302_TIME[2]=BCD_TO_DEC(DS1302_ReadByte(0x86|0x01));//讀取日	
    DS1302_TIME[3]=BCD_TO_DEC(DS1302_ReadByte(0x84|0x01));//讀取時
    DS1302_TIME[4]=BCD_TO_DEC(DS1302_ReadByte(0x82|0x01));//讀取分	
    DS1302_TIME[5]=BCD_TO_DEC(DS1302_ReadByte(0x80|0x01));//讀取秒	
    DS1302_TIME[6]=BCD_TO_DEC(DS1302_ReadByte(0x8a|0x01));//讀取星期
}

2.2 ds1302.h

#ifndef _DS1302_H
#define _DS1302_H
#include "type.h"
#include <reg51.h>
#include "delay.h"
#include "type.h"
#include "uart.h"
#include <intrins.h>

//定義全局函數(shù)
u8 DEC_TO_BCD(u8 val);  //十進制轉BCD碼
u8 BCD_TO_DEC(u8 val);  //BCD碼轉十進制
u8 DS1302_ReadByte(u8 addr);
void DS1302_WriteByte(u8 addr,u8 dat);
void DS1302_WriteTime(u8 year,u8 mon,u8 mday,u8 hour,u8 min,u8 sec,u8 week);
void DS1302_ReadTime(void);
void DS1302_Init(void);
//加入全局變量
extern u8 DS1302_TIME[7];
#endif
  • 更多詳細資料請聯(lián)系.docx
    下載

相關推薦