定时闹钟设计.docx

上传人:b****5 文档编号:29802439 上传时间:2023-07-27 格式:DOCX 页数:25 大小:74.47KB
下载 相关 举报
定时闹钟设计.docx_第1页
第1页 / 共25页
定时闹钟设计.docx_第2页
第2页 / 共25页
定时闹钟设计.docx_第3页
第3页 / 共25页
定时闹钟设计.docx_第4页
第4页 / 共25页
定时闹钟设计.docx_第5页
第5页 / 共25页
点击查看更多>>
下载资源
资源描述

定时闹钟设计.docx

《定时闹钟设计.docx》由会员分享,可在线阅读,更多相关《定时闹钟设计.docx(25页珍藏版)》请在冰豆网上搜索。

定时闹钟设计.docx

定时闹钟设计

电子闹钟的控制系统设计

基于atmega16单片

一、设计目的

此次设计的目的是培养同学们系统地运用已学的理论知识解决实际问题的能力和查阅资料的能力,以及一定的自学能力和独立分析问题、解决问题的能力,能通过独立思考、查阅工具书、参考文献,寻找解决方案;通过完成所选题目的分析与设计,达到技术性能要求。

二、设计要求

1、能显示时时-分分-秒秒。

2、能够设定定时时间、修改定时时间。

3、定时时间到能发出报警声或者启动继电器,从而控制电器的启停。

三、设计的总体结构

3.1整体设计思路

利用Mega16单片机内部时钟作为时间基准,通过软件编程控制可编程器件Mega16单片机,实现秒,分,时,日,月,年的控制,最终通过LCD液晶显示屏显示结果。

此外还可以实现时间调整,定时多种实用功能,整个设计分硬件和软件俩大部分。

硬件部分采用Mega16单片机作为可编程芯片,1602字符液晶作为信号显示;软件部分利用C语言作为设计语言,对Mega16进行编程实现各种功能

3.3软件设计

各部分电路设计

主电路主要就是芯片的运行,加载程序后,在外部时钟的作用下,将按照程序运行,从而可以实现设计的要求,进行时钟时间和定时时间的调整,并且能够在到达定时时间后控制蜂鸣器发出声响。

利用仿真仿真软件画出的电路图

1,显示电路

显示电路即可以让我们看到时间的调整和定时时间的调整,显示调整后的时间。

2仿真电路的总体原理框图

3.3软件设计

软件的设计思路框图

四,C语言程序设计

#include

#defineucharunsignedchar

#defineuintunsignedint

sbitspk=P1^7;

sbitled=P1^5;

sbitDQ=P1^0;

sbitRS=P2^4;

sbitRW=P2^5;

sbitEN=P2^6;

sbitkey1=P2^0;

sbitkey2=P2^1;

sbitkey3=P2^2;

sbitkey4=P2^3;

sbitIO=P3^6;

sbitRST=P3^7;

sbitSCLK=P3^5;

ucharcodetable[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39};

intnian,xing,yue,ri,shi,fen,miao;

ucharnum,temp,c,d,time[7],a,b,aa,bb,ns,ng,ys,yg,rs,rg,ss,sg,fs,fg,ms,mg,flag;

/*******************1602************************/

voiddelay(intz)

{

intx,y;

for(x=z;x>0;x--)

for(y=100;y>0;y--);

}

voidwrite_com(ucharcom)//写命令

{

RS=0;

P0=com;

delay(5);

EN=1;

delay(5);

EN=0;

}

voidwrite_data(uchardate)//写数据

{

RS=1;

P0=date;

delay(5);

EN=1;

delay(5);

EN=0;

}

voidinit()//初始化

{

RW=0;

EN=0;

write_com(0x38);//显示模式设置

write_com(0x0c);//开显示不显示光标不闪

write_com(0x06);//写一个字符地址指针光标加一整屏不移动

write_com(0x01);//显示清零

write_com(0x80+0x04);

write_data('2');

write_com(0x80+0x05);

write_data('0');

write_com(0x80+0x00);

write_data('c');

write_com(0x80+0x01);

write_data('a');

write_com(0x80+0x02);

write_data('i');

write_com(0x80+0x4e);

write_data(0xdf);

write_com(0x80+0x4f);

write_data('C');

write_com(0x80+0x4b);

write_data(0x2e);//显示"。

"

}

/**************DS18B20****************/

voiddelay1(unsignedintt)//延时函数

{

while(t--);

}

voidinit1()//初始化

{

ucharn=0;

DQ=1;//DQ复位

delay1(8);

DQ=0;//主机将DQ拉低

delay1(80);//大于480us的延时

DQ=1;

delay1(5);//延时15~60us

n=DQ;

delay1(5);//若n=0初始成功n=1初始失败(可设置返回值查看n是否为1)

}

voidwrite_byte(uchardat)//写入一个字节

{

uinti;

for(i=0;i<8;i++)

{

DQ=0;

DQ=dat&0x01;

delay1(12);

DQ=1;

dat>>=1;

}

delay1(4);

}

ucharread_byte()//读入一个字节

{

uintk=0;

ucharvalue=0;

for(k=0;k<8;k++)

{

DQ=0;

value>>=1;

DQ=1;

if(DQ)

value|=0x80;

delay1(4);

}

returnvalue;

}

ucharread_temp()//读取温度函数

{

uchara=0,b=0;

init1();

write_byte(0xcc);

write_byte(0x44);

delay1(200);

init1();

write_byte(0xcc);

write_byte(0xbe);

a=read_byte();

b=read_byte();

c=b;

d=a;

b<<=4;

b+=(a&0xf0)>>4;

returnb;

}

/***********************1302**********************/

voidwirte_byte1(uchardate)//写入一个字节

{

uchari;

for(i=8;i>0;i--)

{

IO=date&0x01;

SCLK=0;

SCLK=1;

date=date>>1;

}

}

ucharread_byte1()//读一个字节

{

uchardat,i;

for(i=8;i>0;i--)

{

dat=dat>>1;

SCLK=0;

if(IO)

dat=dat|0x80;

SCLK=1;

}

return(dat);

}

voidwrite_ds1302(ucharadd,uchardate)//将数据写入1302中

{

RST=0;

SCLK=0;

RST=1;

wirte_byte1(add);

wirte_byte1(date);

RST=0;

SCLK=1;

}

ucharread_ds1302(ucharadd)//读出1302中数据

{

uchartemp;

RST=0;

SCLK=0;

RST=1;

wirte_byte1(add);

temp=read_byte1();

RST=0;

SCLK=0;

return(temp);

}

ucharhuan_BCD(uintz)//将数据转换成BCD

{

uinta,b;

a=z/10;

b=z%10;

a=a&0xff;

b=b&0xff;

a<<=4;

a=a|b;

return(a);

}

voidxian_shi()//液晶显示函数

{

if(b==0&a==0)

{

ms=time[0]/16;

mg=time[0]%16;

fs=time[1]/16;

fg=time[1]%16;

fen=fs*10+fg;

ss=time[2]/16;

sg=time[2]%16;

shi=ss*10+sg;

rs=time[3]/16;

rg=time[3]%16;

ri=rs*10+rg;

ys=time[4]/16;

yg=time[4]%16;

yue=ys*10+yg;

ns=time[6]/16;

ng=time[6]%16;

nian=ns*10+ng;

xing=time[5];

}

if(a==1|b==1)

{

ss=shi/10;

sg=shi%10;

write_com(0x80+0x41);

write_data(0xff);

write_com(0x80+0x40);

write_data(table[ss]);

write_com(0x80+0x41);

write_data(table[sg]);

}

if(a==2|b==2)

{

fs=fen/10;

fg=fen%10;

write_com(0x80+0x44);

write_data(0xff);

write_com(0x80+0x43);

write_data(table[fs]);

write_com(0x80+0x44);

write_data(table[fg]);

}

if(a==3)

{

rs=ri/10;

rg=ri%10;

write_com(0x80+0x0d);

write_data(0xff);

write_com(0x80+0x0c);

write_data(table[rs]);

write_com(0x80+0x0d);

write_data(table[rg]);

}

if(a==4)

{

ys=yue/10;

yg=yue%10;

write_com(0x80+0x0a);

write_data(0xff);

write_com(0x80+0x09);

write_data(table[ys]);

write_com(0x80+0x0a);

write_data(table[yg]);

}

if(a==5)

{

ns=nian/10;

ng=nian%10;

write_com(0x80+0x07);

write_data(0xff);

write_com(0x80+0x06);

write_data(table[ns]);

write_com(0x80+0x07);

write_data(table[ng]);

}

if(a==6)

{

write_com(0x80+0x0f);

write_data(0xff);

write_com(0x80+0x0f);

write_data(table[xing]);

}

write_com(0x80+0x06);//在液晶第一行第七八位显示年

write_data(table[ns]);

write_com(0x80+0x07);

write_data(table[ng]);

write_com(0x80+0x08);

write_data('-');

write_com(0x80+0x09);//在液晶第一行第十十一位显示月

write_data(table[ys]);

write_com(0x80+0x0a);

write_data(table[yg]);

write_com(0x80+0x0b);

write_data('-');

write_com(0x80+0x0c);//在液晶第一行第十三十四位显示日

write_data(table[rs]);

write_com(0x80+0x0d);

write_data(table[rg]);

write_com(0x80+0x0f);//在液晶第一行第十七位显示星期

write_data(table[xing]);

write_com(0x80+0x40);//在液晶第二行第二三位显示时

write_data(table[ss]);

write_com(0x80+0x41);

write_data(table[sg]);

write_com(0x80+0x42);

write_data(':

');

write_com(0x80+0x43);//在液晶第二行第五六位显示分

write_data(table[fs]);

write_com(0x80+0x44);

write_data(table[fg]);

write_com(0x80+0x45);

write_data(':

');

write_com(0x80+0x46);//在液晶第二行第八九位显示秒

write_data(table[ms]);

write_com(0x80+0x47);

write_data(table[mg]);

}

voidkeyscan()//按键设置函数可任意设置年月日时分秒星期的数值

{

if(key4!

=0)

{

if(key1==0)//key1按键选择需设置的位

{

if(key1==0)

{

a++;

delay

(1);

}

while(!

key1)

{

delay

(1);

}

}

if(a!

=0)

{

if(key2==0)//key2按键可将需设置的数调大

{

if(a==1)

{

shi++;

if(shi>=24)

{

shi=0;

}

}

if(a==2)

{

fen++;

if(fen>=60)

{

fen=0;

}

}

if(a==3)

{

ri++;

if(ri>=32)

{

ri=1;

}

}

if(a==4)

{

yue++;

if(yue>=12)

{

yue=1;

}

}

if(a==5)

{

nian++;

if(nian>=99)

{

nian=0;

}

}

if(a==6)

{

xing++;

if(xing>=8)

{

xing=1;

}

}

}

if(key3==0)//key3按键可将需设置的数调小

{

if(a==1)

{

shi--;

if(shi<0)

{

shi=23;

}

}

if(a==2)

{

fen--;

if(fen<0)

{

fen=59;

}

}

if(a==3)

{

ri--;

if(ri<1)

{

ri=31;

}

}

if(a==4)

{

yue--;

if(yue<1)

{

yue=12;

}

}

if(a==5)

{

nian--;

if(nian<0)

{

nian=99;

}

}

if(a==6)

{

xing--;

if(xing<1)

{

xing=7;

}

}

}

if(a==7)//当按下key17次后将个数据写入1302

{

a=0;

write_ds1302(0x8e,0x00);//WP=0写操作

write_ds1302(0x80,0x00);//0x80是写秒数据

write_ds1302(0x82,huan_BCD(fen));//0x82是写分数据

write_ds1302(0x84,huan_BCD(shi));//0x84是写时数据

write_ds1302(0x86,huan_BCD(ri));//0x84是写日数据

write_ds1302(0x88,huan_BCD(yue));//0x84是写月数据

write_ds1302(0x8a,huan_BCD(xing));//0x84是写星期数据

write_ds1302(0x8c,huan_BCD(nian));//0x84是写年数据

write_ds1302(0x8e,0x80);//WP=1写保护

}

}

}

}

voidnaozhong()//通过按键设置闹钟时分

{

if(key1!

=0)

{

if(key4==0)

{

if(key4==0)

{

b++;

delay

(1);

}

while(!

key4)

{

delay

(1);

}

}

if(b!

=0)

{

if(key2==0)//key2按键可将需设置的数调大

{

if(b==1)

{

shi++;

if(shi>=24)

{

shi=0;

}

}

if(b==2)

{

fen++;

if(fen>=60)

{

fen=0;

}

}

}

if(key3==0)//key3按键可将需设置的数调小

{

if(b==1)

{

shi--;

if(shi<0)

{

shi=23;

}

}

if(b==2)

{

fen--;

if(fen<0)

{

fen=59;

}

}

}

aa=huan_BCD(shi);//将设置的时钟赋值给aa

bb=huan_BCD(fen);//将设置的分钟赋值给bb

if(b==3)//当按下key43次后闹钟设置完成

{

b=0;

}

}

}

}

voidmain()

{

uinti,temp;

init();

TMOD=0x10;

EA=1;

TH1=(65536-51200)/256;

TL1=(65536-51200)%256;

ET1=1;

while

(1)

{

temp=0x81;//读的初始地址

for(i=0;i<7;i++)//分别把秒分时日月年星期数据读出分7次读好一次地址加2"temp+=2;"

{

time[i]=read_ds1302(temp);

temp+=2;

}

if(bb==time[1]&aa==time[2]&!

time[0])//如果读出来的时钟分钟与1302读出来的值相等且读出来的秒钟为零时进入中断

{

TR1=1;

flag=1;//标志位设置为1

}

if(key3==0)//进入闹钟后可由key3按下停止中断标志位置零允许调时闹钟设置按键动作停止闹铃

{

led=1;

spk=1;

flag=0;

TR1=0;

}

if(flag!

=1)//当进入闹钟中断后调时与设置闹钟的按键无效

{

naozhong();

keyscan();

}

xian_shi();

temp=read_temp();

write_com(0x80+0x49);

write_data(table[temp/10]);//在液晶第二行第十位显示温度的十位

write_com(0x80+0x4a);

write_data(table[temp%10]);//在液晶第二行第十一位显示温度的个位

write_com(0x80+0x4c);

write_data(table[(d&0x0f)*625/1000]);//在液晶第二行第十三位显示温度的小数点后一位

write_com(0x80+0x4d);

write_data(table[(d&0x0f)*625/100%10]);//在液晶第二行第十四位显示温度的小数点后二位

}

}

voidtimer1()interrupt3//定时器

{

uintt;

TH1=(65536-50000)/256;

TL1=(65536-50000)%256;

t++;

spk=0;//蜂鸣器发出滴答声

led=!

led;//发光二极管不停闪烁

delay1(10);

if(t==1120)//约1分钟后闹钟自动停止标志位

{

led=1;

spk=1;

t=0;

TR1=0;

flag=0;

}

}

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 表格模板 > 表格类模板

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1