单片机 智能广告牌设计 金沙滩 51 仿真 实物

智能广告牌设计
可选择左右屏幕移动
通过串口修改字幕内容
显示实时时间和温度
在这里插入图片描述

在这里插入图片描述


#include <reg52.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int rtc_hour = 16, rtc_min = 59, rtc_sec = 55;  /* 时间 */


bit		flag1s	= 0;                    /* 1s定时标志 */
unsigned char	T0RH	= 0;                    /* T0重载值的高字节 */
unsigned char	T0RL	= 0;                    /* T0重载值的低字节 */

unsigned char count_str = 0;                    /* 计数多少个字符 */

void ConfigTimer0( unsigned int ms );


unsigned char IntToString( unsigned char *str, int dat );


extern bit Start18B20();


extern bit Get18B20Temp( int *temp );


extern void InitLcd1602();


extern void LcdShowStr( unsigned char x, unsigned char y, unsigned char *str );


void dis_time();                /* 刷新时间显示 */


void display( char num );       /* 显示一个字符串 */


void SerInit( void );           /* 初始化串口 */


char	start_char_num	= 0;
char	zifu1[16]		= "123456789aqwerty";


sbit	out	= P2 ^ 3;
sbit	key_in1 = P2 ^ 4;


void main()
{
    
    
	bit		res;
	int		temp;           /* 读取到的当前温度值 */
	int		intT, decT;     /* 温度值的整数和小数部分 */
	unsigned char	len;
	unsigned char	str[12];
	char		dir = 0;


	out = 0;                        /* 输出低电平 */

	EA = 1;                         /* 开总中断 */
	ConfigTimer0( 10 );             /* T0定时10ms */
	Start18B20();                   /* 启动DS18B20 */
	InitLcd1602();                  /* 初始化液晶 */
	SerInit();

	while ( 1 )
	{
    
    
		if ( key_in1 == 0 )
		{
    
    
			if ( key_in1 == 0 )
			{
    
    
				while ( key_in1 == 0 )
					;
				dir = !dir;
				start_char_num=2;
			}
		}
		if ( flag1s )                                                   /* 每秒更新一次温度 */
		{
    
    
			TR0	= 0;                                            /* 短暂关闭计时 防止冲突 */
			flag1s	= 0;
			res	= Get18B20Temp( &temp );                        /* 读取当前温度 */
			if ( res )                                              /* 读取成功时,刷新当前温度显示 */
			{
    
    
				intT		= temp >> 4;                    /* 分离出温度值整数部分 */
				decT		= temp & 0xF;                   /* 分离出温度值小数部分 */
				len		= IntToString( str, intT );     /* 整数部分转换为字符串 */
				str[len++]	= '.';                          /* 添加小数点 */
				decT		= (decT * 10) / 16;             /* 二进制的小数部分转换为1位十进制位 */
				str[len++]	= decT + '0';                   /* 十进制小数位再转换为ASCII字符 */
				while ( len < 6 )                               /* 用空格补齐到6个字符长度 */
				{
    
    
					str[len++] = ' ';
				}
				str[len] = '\0';                                /* 添加字符串结束符 */
				LcdShowStr( 0, 0, str );                        /* 显示到液晶屏上 */
			}else {
    
                                                     /* 读取失败时,提示错误信息 */
				LcdShowStr( 0, 0, "error!" );
			}
			Start18B20();                                           /* 重新启动下一次转换 */


			if ( dir == 0 )
			{
    
    
				start_char_num++;                               /* 从哪里开始显示 */
				if ( start_char_num >= 16 )
				{
    
    
					start_char_num = 0;
				}
				display( start_char_num );                      /* 显示哪一个字符 从哪开始显示 */
			}else{
    
    
				start_char_num--;                               /* 从哪里开始显示 */
				if ( start_char_num == -1 )
				{
    
    
					start_char_num = 15;
				}
				display( start_char_num );                      /* 显示哪一个字符 从哪开始显示 */
			}


			TR0 = 1;                                                /* 打开计时 */
		}
	}
}


/* 整型数转换为字符串,str-字符串指针,dat-待转换数,返回值-字符串长度 */
unsigned char IntToString( unsigned char *str, int dat )
{
    
    
	signed char	i	= 0;
	unsigned char	len	= 0;
	unsigned char	buf[6];

	if ( dat < 0 )                          /* 如果为负数,首先取绝对值,并在指针上添加负号 */
	{
    
    
		dat	= -dat;
		*str++	= '-';
		len++;
	}
	do                                      /* 先转换为低位在前的十进制数组 */
	{
    
    
		buf[i++]	= dat % 10;
		dat		/= 10;
	}
	while ( dat > 0 );
	len += i;                               /* i最后的值就是有效字符的个数 */
	while ( i-- > 0 )                       /* 将数组值转换为ASCII码反向拷贝到接收指针上 */
	{
    
    
		*str++ = buf[i] + '0';
	}
	*str = '\0';                            /* 添加字符串结束符 */

	return(len);                            /* 返回字符串长度 */
}


/* 配置并启动T0,ms-T0定时时间 */
void ConfigTimer0( unsigned int ms )
{
    
    
	unsigned long tmp;                      /* 临时变量 */

	tmp	= 11059200 / 12;                /* 定时器计数频率 */
	tmp	= (tmp * ms) / 1000;            /* 计算所需的计数值 */
	tmp	= 65536 - tmp;                  /* 计算定时器重载值 */
	tmp	= tmp + 12;                     /* 补偿中断响应延时造成的误差 */
	T0RH	= (unsigned char) (tmp >> 8);   /* 定时器重载值拆分为高低字节 */
	T0RL	= (unsigned char) tmp;
	TMOD	&= 0xF0;                        /* 清零T0的控制位 */
	TMOD	|= 0x01;                        /* 配置T0为模式1 */
	TH0	= T0RH;                         /* 加载T0重载值 */
	TL0	= T0RL;
	ET0	= 1;                            /* 使能T0中断 */
	TR0	= 1;                            /* 启动T0 */
}


/* T0中断服务函数,完成1秒定时 */
void InterruptTimer0() interrupt 1
{
    
    
	static unsigned char tmr1s = 0;

	TH0	= T0RH;                         /* 重新加载重载值 */
	TL0	= T0RL;
	tmr1s++;
	if ( tmr1s >= 100 )                     /* 定时1s */
	{
    
    
		tmr1s	= 0;
		flag1s	= 1;
		rtc_sec++;                      /* 秒针 */
		if ( rtc_sec == 60 )
		{
    
    
			rtc_sec = 0;
			rtc_min++;              /* 分针 */
			if ( rtc_min == 60 )
			{
    
    
				rtc_min = 0;
				rtc_hour++;     /* 时针   */
				if ( rtc_hour == 24 )
				{
    
    
					rtc_hour = 0;
				}
			}
		}
		/* /刷新时间的显示 */
		dis_time();
	}
}


void Uart_isr() interrupt 4                             /* 中断接收程序 */
{
    
    
	char Txd_data = 0;

	if ( RI )                                       /* 判断是否接收完,接收完成后,由硬件置RI位 */
	{
    
    
		Txd_data	= SBUF;                 /* 读入缓冲区 */
		RI		= 0;                    /* RI清标志 */

		if ( Txd_data == '~' )                  /* 清空数组 */
		{
    
    
			memset( zifu1, ' ', 16 );
			count_str = 0;
		}else{
    
    
			zifu1[count_str++] = Txd_data;  /* 字符存入 */
		}
	}
}

//刷新显示时间 的时分秒 程序

void dis_time()
{
    
    
	unsigned char	shuzu1[20];
	unsigned char	count = 0;

	count = 0;

	shuzu1[count++] = '0' + rtc_hour / 10;
	shuzu1[count++] = '0' + rtc_hour % 10;
	shuzu1[count++] = ':';

	shuzu1[count++] = '0' + rtc_min / 10;
	shuzu1[count++] = '0' + rtc_min % 10;

	shuzu1[count++] = ':';

	shuzu1[count++] = '0' + rtc_sec / 10;
	shuzu1[count++] = '0' + rtc_sec % 10;

	shuzu1[count++] = 0;

	LcdShowStr( 7, 0, shuzu1 );
}


/* zifu = 0 1 2 */
void display( char num )
{
    
    
	char		count = 0;
	unsigned char	dis_str[17];
	char		changdu = 0;
	char		jutis	= 0;


	changdu = num;  /* 从哪一个字符开始显示 */
	jutis	= 16;   /* 这个字符串一共多长 */


	/* 循环装一个字符串dis_str  装满 */
	for ( count = 0; count < 16; count++ )
	{
    
    
		if ( changdu < jutis )
		{
    
    
			dis_str[count] = zifu1[changdu];
			changdu++;
		}else{
    
    
			changdu		= 0;
			dis_str[count]	= zifu1[changdu];
			changdu++;
		}
	}


	LcdShowStr( 0, 1, dis_str );
}





猜你喜欢

转载自blog.csdn.net/x1131230123/article/details/108547825