Holtek合泰单片机《二 & 四》使用lcd1602实现简单的万年历

这次实验纯粹是为了玩。- -!
结合二、四中的学习经验并总结并完成了实验。
因为比较萌新,所以多练习练习。
参考文献:https://blog.csdn.net/hjf161105/article/details/70941441

#include <HT66F70A.h>
#include "type.h"

#define pc     _pcc           //设置c端口模式
#define pd     _pdc           //设置d端口模式
#define rs     _pd1           //定义rs使能端口
#define rw     _pd2           //定义rw读写端口
#define e      _pd3           //定义e端口,高脉冲使能,脉宽最小150ns
#define led_c  _pc            //连接1602的DB0~DB7

void delay_us(uint);          //延时函数3
void led_wr_data(uchar);      //写数据
void led_wr_com(uchar);       //写指令
void led_init();              //1602初始化
void tm0_init();               //tm定时器初始化
void led_wr_string(uchar x, uchar y, char *s); //选择位置写数据
void led_wr_time(uchar x, uchar y, uchar c);    //选择位置写数据

uchar hour=9,min=28,sec=0;
uchar yue=5,ri=7;
uint nian = 2019;
volatile uint count;

void main()
{
	_wdtc=0b10101111;         //关狗
	pd=0x0;                   //d端口为输出模式
	pc=0x0;                   //c端口为输出模式        
	count = 2000;           
	delay_us(1);                    
	led_init();
	tm0_init();
	while(1)
	{
		led_wr_string(0, 0, "date:");
		led_wr_time(5, 0, nian/1000+48);
		led_wr_time(6, 0, nian%1000/100+48);
		led_wr_time(7, 0, nian%100/10+48);
		led_wr_time(8, 0, nian%10+48);
		led_wr_time(9, 0, '-');		
		led_wr_time(10, 0, yue/10+48);
		led_wr_time(11, 0, yue%10+48);
		led_wr_time(12, 0, '-');		
		led_wr_time(13, 0, ri/10+48);
		led_wr_time(14, 0, ri%10+48);					
		
		led_wr_string(0, 1, "Time:");
		led_wr_time(5, 1, hour/10+48);
		led_wr_time(6, 1, hour%10+48);
		led_wr_time(7, 1, '-');
		led_wr_time(8, 1, min/10+48);
		led_wr_time(9, 1, min%10+48);
		led_wr_time(0xa, 1, '-');
		led_wr_time(0xb, 1, sec/10+48);
		led_wr_time(0xc, 1, sec%10+48);
    }
}	
void delay_us(uint time)      //延时函数time us
{
	int i;
	for(i=0;i<time;i++)
	GCC_DELAY(2);
}

void led_wr_data(uchar dat)   //写、显示数据
{	  
	rs=1;
	rw=0;                    
	e=0;                      //rs=1,rw=0 写数据
	delay_us(1);                              
	led_c=dat;               
	delay_us(1);
	e=1;                      //高脉冲使能             
	delay_us(1);
	e=0;
}

void led_wr_com(uchar cdat)   //写指令    
{
	rs=0;                     
	rw=0;
	e=0;                      //rs=0,rw=0 写指令
	delay_us(1);                    
    led_c=cdat;               
	delay_us(1);
	e=1;                      //高脉冲使能
	delay_us(1);
	e=0;
}

void led_init()               //初始化led    0.5ms
{
	
	led_wr_com(0x38);         //0011 1000 8位数据总线DB7~DB0、2行显示模式
	delay_us(1);
	led_wr_com(0x0c);         //0000 1100 开显示,关光标(关光标的显示,其实还有,看不见)
    delay_us(1);
	led_wr_com(0x06);         //0000 0110 显示不移位,光标右移
	delay_us(1);
    led_wr_com(0x01);         //0000 0001 清屏
    delay_us(1);            
}

void tm0_init()				  //定时器初始化
{
    _tm0c0=0x00;           //TM0  FsYs/4=0.5us
    _tm0c1=0xc1;           //定时/计数器模式与A配对
    _tm0al=0x8f;
    _tm0ah=0x03;           //比较器初值d1000
	_t0on=1;               //开定时器
	_t0ae=1;               //tm0,比较器A中断使能	
	_mf0e=1;               //多功能中断使能
	_emi=1;                //开总中断
}  

void led_wr_string(uchar x, uchar y, char *s)   //x 为横坐标 ,y为纵坐标 s写数据(字符显示) 
{
	if(y == 0)
	{
		led_wr_com(0x80+x);
	}
	else
	{
		led_wr_com(0xC0+x);
	}
	while(*s)
	{
		led_wr_data(*s);
		*s++;
	}
}

void led_wr_time(uchar x, uchar y, uchar c)      //x 为横坐标 ,y为纵坐标 c写数据(时间)
{
	if(y == 0)
	{
		led_wr_com(0x80+x);
	}
	else
	{
		led_wr_com(0xC0+x);
	}
	led_wr_data(c);
}

void __attribute((interrupt(0x14))) tim0_int(void)  
{ 
	_emi=0;                 //关总中断
	_t0af=0;   	            //清除TM2比较器A中断标志位
    count--;
    if(!count)
	{
		count = 2000;
		sec++;
	}
	if(sec >= 60)
	{
		sec = 0;
		min++;
	}
	if(min >= 60)
	{
		min = 0;
		hour++;
	}
	if(hour >= 24)
	{
		hour = 0;
		ri++;
	}
	if(ri > 31)
	{
		ri = 0;
		yue++;
	}
	if(yue > 13)
	{
		yue = 0;
		nian++;
	}
	_emi=1;			        //开总中断
}
上一篇:在CSDN的第100篇(^-^)V


下一篇:学期总结