基于PIC16F887单片机的温度时钟显示以及闹钟功能.docx
- 文档编号:9056201
- 上传时间:2023-02-03
- 格式:DOCX
- 页数:35
- 大小:175.59KB
基于PIC16F887单片机的温度时钟显示以及闹钟功能.docx
《基于PIC16F887单片机的温度时钟显示以及闹钟功能.docx》由会员分享,可在线阅读,更多相关《基于PIC16F887单片机的温度时钟显示以及闹钟功能.docx(35页珍藏版)》请在冰豆网上搜索。
基于PIC16F887单片机的温度时钟显示以及闹钟功能
基于PIC16F887单片机的温度、时钟显示以及闹钟功能
基于PIC16F887单片机的温度、时钟
显示以及闹钟功能一、课程设计的目的
《PIC单片机课程设计》是电气工程及其自动化专业及相近专业的一门重要的专业实践课,本课程在《PIC单片机》课程的基础上,通过硬件设计与软件编程与调试的实践,进一步掌握PIC单片机的应用方法,熟练PIC单片机的C程序的编写与调试,是毕业设计前的一次重要的实践,为今后走上工作岗位打下坚实的单片机应用基础。
二、设计内容
1Proteus线路图绘制
根据所设计的线路图,绘制与之一致的,能用于仿真的Proteus线路图。
一致。
要求所绘的线路图美观、紧凑,参数要与课设
2、软件编制与调试
根据所设计的线路图制相应的单片机C程序,要求所制的程序符合C语言
译,有错及时修改,并先在Proteus上仿真,格式并加上注解。
每编一段即进行
基本正确后再用PICkit3在线调试,最后应脱机运行。
三、设计目标
1该设计包括数字钟及数字温度计:
按键的使用.LCD.蜂鸣器时钟芯片DS1307和温度传感器TC74。
2功能;此设计可以感测环境的温度,显示当前的时间,及闹钟。
温度与时间都显示在LCD显示屏上,以及如何调整闹钟界面
四硬件设计及说明
1复位按键
2时钟芯片DS1307及附属接线
时钟芯片DS1307用于产生时间,它提供了秒、分、时、日、年、和星期等数据,能算只瑞年2100年,时钟的晶振是典型的32.768Hz。
(1)其引脚作用如下:
2
(2)DS1307的读写如下;
1写DS1307的步骤如下:
a)发送启始位;
b)发送DS1307的7位地址+0(写),即0b11010000;
c)发送要写入DS1307的地址,地址见图16,如要修改分,此值为1;
d)发送要写入DS1307的数,如要把分修改为十进制数37,则此数为0x37;
e)发送停止位;
2读DS1307的步骤如下:
a)发送启始位;
b)发送DS1307的7位地址+0(写),即0b11010000;
c)发送要读的DS1307的起始地址,如要从秒读起,为0;
d)发送停止位;
e)发送重新开始位;
f)发送DS1307的7位地址+1(读),即0b11010001;
g)发送读使能位,接收一个数据,单片机发送应答位;
h)发送读使能,接收下一个数据(地址会自动+1),单片机发送应答位,直到读数完成,接收最后
一个数时单片机不发送应答位;
i)发送停止位;
注意在DS1307仿真的时候七位地址为0b1001101而实际为0b1001000;(3)功能是;提供时间通过pic16F877送入LCD中显示。
3振荡方式
4时钟控制按键及闹钟电路
(1)按键1可以再时钟界面和闹钟界面切换
(2)按键2可以通过光标移动设置时间和闹钟(3)按键3,4可以修改时机
(4)三极管用于电流的放大,以致驱动喇叭。
5LM016L液晶显示屏
LM016L是字符型的LCD液晶显示屏其内部控制芯片是HD44780或KS0066之类是16X2的字符型的LCD
对其使用时
(1)要初始化;
(2)在LCD显示前,要对显示位置进行定位,既写位置命令(3)把该命令写入到DDRAM中
(4)在用写数据命令,显示要显示的字符
五软件设计及说明
程序大体说明,
1.设单片机上电,屏幕上显示welcome~~和hello!
!
2.上述界面延迟一段时间后,自动进入时间界面,通过程序的运行,单片机自动同DS1307和TC74芯片中读取时间和温度并显示在LCD上
3.通过不断的按键扫面,当
(1)按键1可以再时钟界面和闹钟界面切换
(2)按键2可以通过光标移动设置时间和闹钟
(3)按键3,4可以修改时间,分别加减
4.当切换到闹钟界面,通过设置好时间后,在时间界面星期旁边会显示一个A提示我们闹钟已经开启,当到了设置的时间点,蜂鸣器会自动响,延迟一段时间
会自动关掉,或者我们可以用通过按键4人为关掉它#include
__CONFIG(0x20F1);
#defineucharunsignedchar#defineuintunsignedint#defineds13070b1101000
#defineTC740b1001000#defineRTR0b00000000#defineFMQRC1
#defineLCD_RSRD4
#defineLCD_RWRD5
#defineLCD_ERD6
#defineS1RB0
#defineS2RB1
#defineS3RB2
#defineS4RB3
#defineDAT1
#defineCOM0
#defineLINE10b10000000#defineLINE20b11000000#defineYEARLINE1+2#defineMONTHLINE1+5#defineDAYLINE1+8#defineWEEKDAY+3#defineHOURLINE2+1#defineMINUTELINE2+4#defineSECONDLINE2+7#defineWENDUSECOND+4//函数声明
voidDELAY(uintn);voidDELAY_A(uintn);voidDELAY_US(charn);voidCSH();
voidDS1307_CSH();
voidKEYSCAN();
voidLCD_CSH();
voidLCD_BUSY();
voidLCD_CLR();
voidLCD_GD();
voidREAD();
voidDSweek(char);
voidLCD_WRITE(char,char);
voidLCD_WRITE_4(char,char);voidTIME();
voidTIME_UP();
voidTIME_DOWN();
voidTIME_UPDATE();
voidDISL1();
voidDISL2();
voidDISL5();
voidBCD(uint);
voidDISP_T(signedchar);voidIIC_CSH();
voidIIC_SEND(charR);
voidIIC_WRITE(char,char);voidALARM_CLOCK();
voidALARM_KG();
charLCD_READ();
charIIC_READ(charaddr);charflag,flag_A,A;
charm=0,f=0,s=0,x,r,y,n;charA_m=0,A_f=0,A_s=0,A_x=0;charshi,ge;
charBW,SW,GW;
signedcharT_READ();
ucharnum1=0,num2=0,num3;constuchartable0[]={"WELCOME!
!
"};
constuchartable01[]={"HELLO!
!
"};
constuchartable04[]={"SETTIME"};
constuchartable[]={"20--"};
constuchartable1[]={":
:
"};//BCD码转换,R1双字节转换为十进制数
voidBCD(uintR1)
{BW=0;SW=0;GW=0;
while(R1>=100)
{R1-=100;BW++;}
while(R1>=10)
{R1-=10;SW++;}
GW=R1;
}
//清屏
voidLCD_CLR()
{LCD_WRITE(0b00000001,COM);
DELAY
(2);
}
//延时子程序
voidDELAY(uintn)
{uintj;
chark;
for(j=0;j for(k=246;k>0;k--)NOP(); } //关闹钟 voidDELAY_A(uintn) {uintj; chark; for(j=0;j {if(S4==0) {DELAY(20); if(S4==0) {break;} } for(k=246;k>0;k--) {NOP(); if(S4==0) {DELAY(20); if(S4==0) {break;} } } } } voidDELAY_US(charn){charj; j=n; while(j>0) {j--; NOP();NOP();NOP();NOP(); } } //初始化 voidCSH() { TRISC=0b00011000; TRISD=0X00; ANSELH=0b000000; TRISB=0b11111111; RBPU=0;//B口上拉使能 WPUB=0b11111111;//887必须设置 PORTB=0XFF; RC1=0; RD7=1; LCD_CSH(); IIC_CSH(); DISL1(); DISL2(); DELAY(500); LCD_CLR(); LCD_GD(); DS1307_CSH(); } //LCD模块初始化 voidLCD_CSH() DELAY(20);//延时20ms{ LCD_WRITE_4(0b0011,COM);//发送控制序列 DELAY (1);//延时1ms LCD_WRITE_4(0b0011,COM);//发送控制序列 DELAY_US(10);//延时100us LCD_WRITE_4(0b0011,COM);//发送控制序列 DELAY_US(10);//延时100us LCD_WRITE_4(0b0010,COM);//4位数据格式 LCD_BUSY();//LCD忙检测 LCD_WRITE(0b00101000,COM);//4位数据格式,2行(实际上4行! ),5 ×7点阵 LCD_WRITE(0b00001100,COM);//D(d2)=1: 打开显示,C(d1)=1: 光标打 开,B(d0)=1: 光标闪烁 LCD_CLR(); LCD_WRITE(0b00000110,COM);//输入模式,I/D(d1)=1: 地址加 1,S(d0)=1: 显示移位关闭 } //LCD_GD//固定显示voidLCD_GD() {chari; LCD_WRITE(LINE1,COM); for(i=0;i<11;i++) { LCD_WRITE(table[i],DAT); DELAY (1); } LCD_WRITE(LINE2+1,COM); for(i=0;i<8;i++) { LCD_WRITE(table1[i],DAT); } } //===========DISL1======voidDISL1() {chari; LCD_WRITE(0X80,COM); for(i=0;i<15;i++) { LCD_WRITE(table0[i],DAT); } } //===========DISL2======voidDISL2() {chari; LCD_WRITE(0Xc0,COM); for(i=0;i<15;i++) { LCD_WRITE(table01[i],DAT); } } //===========DISL5======voidDISL5() {chari; LCD_WRITE(0x80,COM); for(i=0;i<15;i++) { LCD_WRITE(table04[i],DAT); } } //LCD_READ//读LCD状态 charLCD_READ() {unsignedcharR1; LCD_RS=0;//寄存器选择 LCD_RW=1;NOP();//读为1 LCD_E=1;NOP();//使能 R1=0;//短延时 R1=PORTD;//读数据的高4位给R1的高4位,低4位清0 R1=(R1<<4)&0XF0; LCD_E=0;NOP();//读数据结束 LCD_E=1;NOP(); R1|=(PORTD&0X0F);//读PORTD的低4位,R1的高4位不变 LCD_E=0;NOP();//读数据结束 LCD_RW=0; return(R1); } //=======写R1的低4位,FLAG为寄存器选择,1为命令,0为数据== voidLCD_WRITE_4(charR1,charFLAG) { NOP();NOP();//短延时 LCD_RW=0;NOP();//写模式 LCD_RS=FLAG;NOP();//寄存器选择 PORTD&=0XF0;NOP();//RD低4位先清0 LCD_E=1;NOP();//使能 R1=R1&0X0F;//低4位 PORTD|=R1;NOP();NOP();//送4位 NOP();NOP();//数据送入有效 LCD_E=0; LCD_RS=0;NOP(); PORTD&=0XF0;//RD低4位清0} //======写1B数R1,FLAG为写命令或数据选择,0为写命令,1为写数据 voidLCD_WRITE(charR1,charFLAG) {charR2; LCD_BUSY();//检测忙否 R2=R1&0XF0;//低4位清0 R2=R2>>4;//取高4位 LCD_WRITE_4(R2,FLAG);//先写高4位 R2=R1&0X0F;//高4位清0,取低4位 LCD_WRITE_4(R2,FLAG);//再送低4位 DELAY_US(10);//延时100us} //检测LCD是否忙 voidLCD_BUSY() { unsignedcharR1; do{ R1=LCD_READ(); }while(R1&0X80); } //发送数R并等待发送完成,收到从机的应答信号208voidIIC_SEND(charR){SSPBUF=R;//发送 while(RW==1);//在主动模式下,判断发送是否完成 while(SSPIF==0);//等待发送完成 while(ACKSTAT==1);//等待从机发送应答信号 } //IIC初始化208 voidIIC_CSH() {TRISC&=0b00011000;//SDA,SCL设置为输入~ SSPCON=0b00101000;//同步串口使能(SSPEN),主控方式 SMP=0;//使能高速模式(400kHz)的压摆率控制 SSPADD=4;//主控模式为波特率值,每位时间 T=(SSPADD+1)/Tcy=5us } //IIC_READ读 charIIC_READ(charaddr){ chariicr; SEN=1; while(SEN==1);//发送起始位 IIC_SEND(0b11010000);//DS1307在总线上的地址: 0b11010000 IIC_SEND(addr);//读取的首地址 RSEN=1; while(RSEN==1);//发送重新起始位 IIC_SEND(0b11010001);//读数据 SSPIF=0; RCEN=1; while(SSPIF==0);//等待读完成 iicr=SSPBUF; ACKDT=1; ACKEN=1; while(ACKEN==1); PEN=1;//发送停止位 while(PEN==0); return(iicr);} //IIC_WRITE写 voidIIC_WRITE(charaddr,chardata) { SEN=1; while(SEN==1); IIC_SEND(0b11010000); IIC_SEND(addr); IIC_SEND(data); PEN=1; while(PEN==1); } //DS1307初始化时间并显示时间 voidDS1307_CSH() { IIC_WRITE(0,0x45);//00秒 IIC_WRITE(1,0x00);//00分 IIC_WRITE(2,0x10);//00时 IIC_WRITE(3,0x06);//星期日 IIC_WRITE(4,0x05);//1日 IIC_WRITE(5,0x05);//1月 IIC_WRITE(6,0x12);//12年 } voidREAD() { LCD_WRITE(SECOND,COM); shi=IIC_READ(0)>>4; ge=IIC_READ(0)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); LCD_WRITE(MINUTE,COM); shi=IIC_READ (1)>>4; ge=IIC_READ (1)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); LCD_WRITE(HOUR,COM); shi=IIC_READ (2)>>4; ge=IIC_READ (2)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); LCD_WRITE(DAY,COM); shi=IIC_READ(4)>>4; ge=IIC_READ(4)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); DSweek(IIC_READ(3)); LCD_WRITE(MONTH,COM); shi=IIC_READ(5)>>4; ge=IIC_READ(5)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); LCD_WRITE(YEAR,COM); shi=IIC_READ(6)>>4; ge=IIC_READ(6)&0x0f; LCD_WRITE(0x30+shi,DAT); LCD_WRITE(0x30+ge,DAT); DELAY(100); DISP_T(T_READ()); if(A==1) { LCD_WRITE(WEEK+4,COM); LCD_WRITE('A',DAT); } if(A! =1) { LCD_WRITE(WEEK+4,COM); LCD_WRITE('',DAT); } } voidDSweek(charnum) { LCD_WRITE(WEEK,COM); switch(num) { case1: LCD_WRITE('M',DAT); LCD_WRITE('0',DAT); LCD_WRITE('N',DAT); break; case2: LCD_WRITE('T',DAT); LCD_WRITE('U',DAT); LCD_WRITE('E',DAT); break; case3: LCD_WRITE('W',DAT); LCD_WRITE('E',DAT); LCD_WRITE('D',DAT); break; case4: LCD_WRITE('T',DAT); LCD_WRITE('H',DAT); LCD_WRITE('U',DAT); break; case5: LCD_WRITE('F',DAT); LCD_WRITE('R',DAT); LCD_WRITE('T',DAT); break; case6: LCD_WRITE('S',DAT); LCD_WRITE('A',DAT); LCD_WRITE('T',DAT); break; case7: LCD_WRITE('S',DAT); LCD_WRITE('U',DAT); LCD_WRITE('N',DAT); break; } } //**********温度模块*************//读温度值 signedcharT_READ(){ signedcharR1; SEN=1; while(SEN==1);//发送起始位 IIC_SEND(0b10010000);//TC74在总线上的地址: 0b10010000 IIC_SEND(RTR); RSEN=1; while(RSEN==1);//发送重新起始位 IIC_SEND(0b10010001);//读数据 RCEN=1; while(RCEN==1);//等待读完成 R1=SSPBUF; PEN=1;//发送停止位 while(PEN==0); return(R1); } //显示温度 voidDISP_T(signedcharR1){charR2; LCD_WRITE(0b00001100,COM); if(R1>=0) BCD(R1); else {R2=~R1+1; BCD(R2); } LCD_WRITE(WENDU,COM); if(R1<0) LCD_WRITE('-',DAT); if(R1>0) LCD_WRITE(0x30+SW,DAT); LCD_WRITE(0x30+GW,DAT); LCD_WRITE(0xDF,DAT); LCD_WRITE('C',DAT); } //闹钟 voidALARM_CLOCK() { PR2=249; CCPR2L=0x25; CCP2CON=0B00001100; T2CO
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 基于 PIC16F887 单片机 温度 时钟 显示 以及 闹钟 功能