03独立按键控制LED移动


一、独立按键控制LED单向移动

代码分为两个部分:“主函数”+“延时函数”,此处列出整体框架,填充部分见下文

include <REGX52.H>  //添加头文件
void Delay(unsigned int xms);   //延时函数声明
void main()
{
	//此处待填充
}
void Delay(unsigned int xms)  //@12.000MHz延时函数(固定的)
{
	unsigned char i, j;
	while(xms) 
	{
		i = 12;
		j = 169;
		do
		{
			while (--j);
		}
		while (--i);
		xms--;
	}
}

单项右移

LEDnum定义为unsigned char是因为这个数据类型正好是8位,对应P2八位寄存器

填充代码如下:

  unsigned char LEDnum; //移位自增or自减
  P2=0xFE;  //初始化使第一个灯亮
	
	while(1)
	{
		if(P3_1==0)  //判断独立按键的开关
		{
			Delay(20);	//延迟消抖
			while(P3_1==0);  //判断松手
			Delay(20);   //延迟消抖
		
			LEDnum++; 
			
			if(LEDnum>=8)  //8位寄存器且没有负值
			{
				LEDnum=0;  //回到起点,超过8程序失效
			}
			P2=~(0x01<<LEDnum); //'<<'为左移符号,取反保证只有一个灯亮,但由于本人开发板上的LED灯是01~08从左至右,故显示出是向右移
		}
	}
}

单项左移

LEDnum定义为unsigned char时,取值不能为负。

  • 第一次选择定义为unsigned char时,判断是否为0,若是则对LEDnum赋值8,从头开始向左移,但最后一个LED总是不能正常亮。
  • 可能原因1:与自增不同,需要先判断是否为0才能自减
  • 第二次LEDnum数据类型不变,依旧为unsigned char,将条件语句补充完整,结果正常

填充代码如下:

	unsigned char LEDnum; 
    P2=0x7F;   //初始化使右侧第一个灯亮,从右至左移动
	while(1)
	{
		if(P3_0==0)  
		{
			Delay(20);	
			while(P3_0==0);  
			Delay(20);   
		
			if(LEDnum==0)  
			{
				LEDnum=7; 
			}
			else 
				LEDnum--;
			P2=~(0x01<<LEDnum);
		}
	}
  • 可能原因2:LEDnum在左侧第二个灯处就自减到0了,重新开始了新的一轮,说明在左侧第一个(即从右至左最后一个)处应该做一个是否为负的判断
  • 第三次选择判断是否为负数,改变LEDnum为int数据类型,判断是否为负值,若是则对LEDnum赋值7(如果为8则会在一轮的结尾空一个),重新测试,可以正常显示。

填充代码如下:

	int LEDnum=8; //移位上限,自减变量
	P2=0x7F;  //初始化使右侧第一个灯亮,从右至左移动
	while(1)
	{
		if(P3_0==0)
		{
			Delay(20);
			while(P3_0==0);
			Delay(20);
			
			LEDnum--;
			if(LEDnum<0)
			{
				LEDnum=7;
			}
			P2=~(0x01<<LEDnum);
		}
	}

二、独立按键控制LED移动

整体代码如下:

#include <REGX52.H>
void Delay(unsigned int xms);   //函数声明
void main()
{
  unsigned char LEDnum; //移位自增or自减
  P2=0xFE;  //初始化使第一个灯亮
	
	while(1)
	{
		if(P3_1==0)  //判断独立按键的开关
		{
			Delay(20);	//延迟消抖
			while(P3_1==0);  //判断松手
			Delay(20);   //延迟消抖
		
			LEDnum++; 
			
			if(LEDnum>=8)  //8位寄存器且没有负值
			{
				LEDnum=0;  //回到起点,超过8程序失效
			}
			P2=~(0x01<<LEDnum); //右移
    
   		 if(P3_0==0)  
		 {
			Delay(20);	
			while(P3_0==0);  
			Delay(20);   
      
			if(LEDnum==0)  
			{
				LEDnum=7; 
			}
			else
		  		LEDnum--;
			P2=~(0x01<<LEDnum); //左移
	      }
	}
}

void Delay(unsigned int xms)  //@12.000MHz延时函数(固定的)
{
	unsigned char i, j;
	while(xms) 
	{
		i = 12;
		j = 169;
		do
		{
			while (--j);
		}
		while (--i);
		xms--;
	}
}

总结

  • 硬件电路与寄存器编辑:寄存器避免人为改换电路的繁琐过程,而是切换输出电平,达到切换导线的目的。与VCC连接是输出1,与GND连接是输出0
  • unsigned char 8位 int 16位
  • 不论左移右移都使用了<<左移符号,因为LEDnum是一个自增自减的量。若<<在自加前提下运行时为左移,则自增为左移,自减为左移少一位,可以看作右移
  • 运行时定义LEDnum总是出错,发现它必须放在主函数的一开始的位置,否则无法创建运行
  • P2口需要初始化,使它从第一个LED开始亮(P2=~0x01取反更方便,当然写P2=0xFE也是正确的)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值