基于C51实现led流水灯

🐋 前言:本实验基于STC89C52RC芯片集成的51单片机,根据电路原理图点亮led灯,同时实现led灯的走马灯效果。由于51系列单片机结构大同小异,读者可根据此博客举一反三,实现所需完成的功能。


🐬 目录:


🐇 实验所选单片机及结构展示(以普中C51为例,其他大同小异),本实验所操作led模块位于图中⑤位置

在这里插入图片描述

🐇 实验效果

一、背景知识

🐪 单片机:是一种集成电路芯片,是采用超大规模集成电路技术把具有数据处理能力的中央处理器CPU、随机存储器RAM、只读存储器ROM等功能集成到一块硅片上构成的一个小而完善的微型计算机系统
在这里插入图片描述

🐪 若要使系统正常运行,必须确保单片机的最小系统稳定工作。51 单片机的最 小系统由以下几部分组成: (1)晶振电路(晶振电路提供时钟给单片机工作,犹如人的心脏)(2)复位电路 (3)电源电路
在这里插入图片描述

🐪 芯片引脚分类:
(1)电源引脚:上图中的VCC、GND都属于电源引脚
(2)晶振引脚:上图中的XTAL1、XTAL@都属于晶振引脚
(3)复位引脚:上图中的RST/VPD属于复位引脚
(4)通信引脚:51单片机串口功能引脚(TXD、RXD)
(5)GPIO引脚:上图中带有Px.x等字样的属于GPIO引脚,共32个,分为4组,每组8个IO
🐺P0 口是漏极开路,要使其输出高电平,必须外接上拉电阻,通常选择 4.7K~10K 阻值。
🐺P0、P1、P2 几乎都用作普通 I/O 口使用,既可作为输入,又可作为输出。
🐺 P3 口既可用作普通 I/O 口,又可作为第二功能使用,比如串口、外部中 断、计数器等。


二、环境搭建(keil4)

新建工程->选择CPU型号(Atmel(AT89C52))->给工程添加文件->配置输出文件hex

在这里插入图片描述

三、点亮一个led灯

💌 3.1 查看电路原理图

在这里插入图片描述
通过观察开发板的线路连接图可以观察到:
☁️ 1.D1阴极连接到单片机的P2.0引脚(线编号相同表示连接在一起P20)、D2连接到单片机P2.1引脚………
☁️ 2.当单片机P2.0输出低电平0,则与电源连接的D1形成通路,D1灯亮。P2.X输出0,其他灯亦然。
因此,要想使得D1等亮,需要编程并将程序烧录到单片机中,使得P2.0端口输出低电平,

💌 3.2 编写代码并烧录

☁️ 3.2.1 导入reg52.h头文件,预编译时会将头文件中的内容加载到文件中,reg52.h头文件中内容如下:

#ifndef __REG52_H__
#define __REG52_H__

/*  BYTE Registers  */
sfr P0    = 0x80;
sfr P1    = 0x90;
sfr P2    = 0xA0;
sfr P3    = 0xB0;
sfr PSW   = 0xD0;
sfr ACC   = 0xE0;
sfr B     = 0xF0;
sfr SP    = 0x81;
sfr DPL   = 0x82;
sfr DPH   = 0x83;
sfr PCON  = 0x87;
sfr TCON  = 0x88;
sfr TMOD  = 0x89;
sfr TL0   = 0x8A;
sfr TL1   = 0x8B;
sfr TH0   = 0x8C;
sfr TH1   = 0x8D;
sfr IE    = 0xA8;
sfr IP    = 0xB8;
sfr SCON  = 0x98;
sfr SBUF  = 0x99;

/*  8052 Extensions  */
sfr T2CON  = 0xC8;
sfr RCAP2L = 0xCA;
sfr RCAP2H = 0xCB;
sfr TL2    = 0xCC;
sfr TH2    = 0xCD;


/*  BIT Registers  */
/*  PSW  */
sbit CY    = PSW^7;
sbit AC    = PSW^6;
sbit F0    = PSW^5;
sbit RS1   = PSW^4;
sbit RS0   = PSW^3;
sbit OV    = PSW^2;
sbit P     = PSW^0; //8052 only

/*  TCON  */
sbit TF1   = TCON^7;
sbit TR1   = TCON^6;
sbit TF0   = TCON^5;
sbit TR0   = TCON^4;
sbit IE1   = TCON^3;
sbit IT1   = TCON^2;
sbit IE0   = TCON^1;
sbit IT0   = TCON^0;

/*  IE  */
sbit EA    = IE^7;
sbit ET2   = IE^5; //8052 only
sbit ES    = IE^4;
sbit ET1   = IE^3;
sbit EX1   = IE^2;
sbit ET0   = IE^1;
sbit EX0   = IE^0;

/*  IP  */
sbit PT2   = IP^5;
sbit PS    = IP^4;
sbit PT1   = IP^3;
sbit PX1   = IP^2;
sbit PT0   = IP^1;
sbit PX0   = IP^0;

/*  P3  */
sbit RD    = P3^7;
sbit WR    = P3^6;
sbit T1    = P3^5;
sbit T0    = P3^4;
sbit INT1  = P3^3;
sbit INT0  = P3^2;
sbit TXD   = P3^1;
sbit RXD   = P3^0;

/*  SCON  */
sbit SM0   = SCON^7;
sbit SM1   = SCON^6;
sbit SM2   = SCON^5;
sbit REN   = SCON^4;
sbit TB8   = SCON^3;
sbit RB8   = SCON^2;
sbit TI    = SCON^1;
sbit RI    = SCON^0;

/*  P1  */
sbit T2EX  = P1^1; // 8052 only
sbit T2    = P1^0; // 8052 only
             
/*  T2CON  */
sbit TF2    = T2CON^7;
sbit EXF2   = T2CON^6;
sbit RCLK   = T2CON^5;
sbit TCLK   = T2CON^4;
sbit EXEN2  = T2CON^3;
sbit TR2    = T2CON^2;
sbit C_T2   = T2CON^1;
sbit CP_RL2 = T2CON^0;

#endif

从上面代码中可以看到,该头文件中定义了 52 系列单片机内部所有的功能 寄存器。其中sbitsfr为C51扩充数据类型。C51扩充数据类型主要如下:
在这里插入图片描述

ssfr P2 = 0xA0;

声明一个8位的特殊功能寄存器,它的起始地址为0xA0

sbit LED1 = P2^0

P2是一个8位寄存器,P2^0表示这个8位寄存器的最低位。该语句的功能就是将P2寄存器的最低位声明为LED1,以后若是要对P2寄存器最低位操作,则可直接操作LED1

☁️ 3.2.2 编写程序
使用while(1)死循环,使得程序一直运行,这样能保证led灯一直亮着。
main.c

#include "reg52.h"

sbit LED1=P2^0;	//将P2.0管脚定义为LED1

void main()
{
	LED1=0;	//将寄存器P2的最低位赋低电平
	while(1)
	{
		
	}		
}

四、实现led灯闪烁

📟 当单片机P2.0引脚输出高电平时,led等两侧无电位差,因此没有电流通过,led灯熄灭。实现程序如下:

#include "reg52.h"

typedef unsigned int u16;	//对系统默认数据类型进行重定义
typedef unsigned char u8;

sbit LED1=P2^0;	//将P2.0管脚定义为LED1

/*******************************************************************************
*函数名      : delay_10us
* 函数功能		 : 延时函数,ten_us=1时,大约延时10us
*******************************************************************************/
void delay_10us(u16 ten_us)
{
	while(ten_us--);	
}

void main()
{	
	while(1)
	{
		LED1=0;	//点亮
		delay_10us(50000); //点亮500ms
		LED1=1;	//熄灭
		delay_10us(50000); 	
	}		
}

五、实现led流水灯

🐙 本实验通过两种方式实现led走马灯效果,一种是通过循环+移位完成对P2寄存器各位轮流赋低电平。第二种是使用intrins,h头文件中定义的外部方法 _crol__cror_分别实现按位的移动

#include "reg52.h"
#include "intrins.h"

typedef unsigned int u16;	//对系统默认数据类型进行重定义
typedef unsigned char u8;

#define LED_PORT	P2	//使用宏定义P2端口寄存器

/*******************************************************************************
* 函数名:       : delay_10us
* 函数功能		 : 延时函数,ten_us=1时,大约延时10us
*******************************************************************************/
void delay_10us(u16 ten_us)
{
	while(ten_us--);	
}

void main()
{	
   	u8 i=0;

	LED_PORT=~0x01;	//给P2寄存器各位赋值,即给寄存器最低位赋低电平
	delay_10us(50000);
	while(1)
	{
		//方式一:通过移位+循环实现流水灯
				for(i=0;i<8;i++)
		{
			LED_PORT=~(0x01<<i);	//给P2寄存器最低位到最高位依次赋低电平,循环8次后继续循环
			delay_10us(50000);
		}
		
		//方式2:使用循环+_crol_或_cror_函数实现流水灯
//		for(i=0;i<7;i++)	 //将led左移一位
//		{									  
//			LED_PORT=_crol_(LED_PORT,1);
//			delay_10us(50000); 	
//		}
//		for(i=0;i<7;i++)	//将led右移一位
//		{
//			LED_PORT=_cror_(LED_PORT,1);
//			delay_10us(50000);	
//		}	
	}		
}

感谢观看,如对内容有疑惑或补充,欢迎留言讨论,共同进步!!!

在这里插入图片描述

  • 18
    点赞
  • 89
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值