05-独立按键的基本操作与扩展应用
05-独立按键的基本操作与扩展应用
在写代码前需做如下,否则独立按键无响应:
由电路图可知:独立按键默认为高电平,当按键按下时为低电平
即S7(P30)、S6(P31)、S5(P32)、S4(P33)
当按下按键时,P3口对应低电平,松开后对应高电平,判断是否一直按下此时需要使用while(1) 死循环,由于是按下点亮,松开熄灭,所以当一直按下时,点亮且进入死循环,否则熄灭
代码如下:
#include <REGX52.H>
sbit s7 = P3^0;
sbit s6 = P3^1;
sbit s5 = P3^2;
sbit s4 = P3^3;
sbit L1 = P0^0;
sbit L2 = P0^1;
sbit L3 = P0^2;
sbit L4 = P0^3;
void _74HC138(unsigned char n) {
switch(n) {
case 4:
P2 = (P2&0x1f) | 0x80; // LED
break;
case 5:
P2 = (P2&0x1f) | 0xa0; //蜂鸣器和继电器
break;
case 6:
P2 = (P2&0x1f) | 0xa0; // 数码管位选
break;
case 7:
P2 = (P2&0x1f) | 0xc0; // 数码管段选
break;
case 0:
P2 = (P2&0x1f) | 0x00; //
break;
}
}
void DelayK(unsigned char t) {
while(t--);
}
void ScanKeys_Alone() {
if(s7 == 0) { //检测是否按下
DelayK(100);
if(s7 == 0) {
L1 = 0;
while(s7==0); // 如果为低电平就一直循环 检测是否松开
L1 = 1;
}
}
if(s6 == 0) { //检测是否按下
DelayK(100);
if(s6 == 0) {
L2 = 0;
while(s6==0); // 如果为低电平就一直循环 检测是否松开
L2 = 1;
}
}
if(s5 == 0) { //检测是否按下
DelayK(100);
if(s5 == 0) {
L3 = 0;
while(s5==0); // 如果为低电平就一直循环 检测是否松开
L3 = 1;
}
}
if(s4 == 0) { //检测是否按下
DelayK(100);
if(s4 == 0) {
L4 = 0;
while(s4==0); // 如果为低电平就一直循环 检测是否松开
L4 = 1;
}
}
}
void main(void) {
_74HC138(4);
while(1) {
ScanKeys_Alone();
}
}
由上可知:该题目意思为S7与S6为状态选择键,且L1与L2分别为S7、S6的状态指示灯,且L1与L2不可同时点亮. 当L1点亮时,S5、S4分别控制L3,L4,当L2点亮时,S5、S4分别控制L5,L6,且按键S5、S4按下后点亮,松开后熄灭
所以此时生声明一个变量stat.且默认stat=0,当S7按下时,将stat赋值为1,且点亮L1,当S6按下时,将stat赋值为2,且点亮L2,再次按下时,熄灭LED灯
当L1点亮时,stat=1,且S5按下时,L3点亮,S4按下时,L4点亮
当L2点亮时,stat=2,且S5按下时,L5点亮,S4按下时,L6点亮
#include <REGX52.H>
sbit s7 = P3^0;
sbit s6 = P3^1;
sbit s5 = P3^2;
sbit s4 = P3^3;
sbit L1 = P0^0;
sbit L2 = P0^1;
sbit L3 = P0^2;
sbit L4 = P0^3;
sbit L5 = P0^4;
sbit L6 = P0^5;
sbit L7 = P0^6;
sbit L8 = P0^7;
void _74HC138(unsigned char n) {
switch(n) {
case 4: // LED
P2 = (P2 & 0x1f) | 0x80;
break;
case 5: //蜂鸣器和继电器
P2 = (P2 & 0x1f) | 0xa0;
break;
case 6: // 数码管位选
P2 = (P2 & 0x1f) | 0xc0;
break;
case 7: // 数码管段选
P2 = (P2 & 0x1f) | 0xe0;
break;
case 0:
P2 = (P2 & 0x1f) | 0x00;
break;
}
}
void DelayK(unsigned int t) {
while(t--);
}
void SystemInit(void) {
_74HC138(5);
P0 = 0x00; // 关闭蜂鸣器和继电器
_74HC138(4);
P0 = 0xff; // 关闭所有LED
}
unsigned char stat_k = 0;
// stat_k = 0
void ScanKey_Alone(void) {
// 当stat_k == 1的时候为s7的控制源
// 当stat_k == 2的时候为s6的控制源
if(s7 == 0) {
DelayK(300);
if(s7== 0) {
if(stat_k == 0) {
DelayK(100);
while(s7==0) {
stat_k = 1;
}
L1 = 0;
DelayK(100);
}else if(stat_k == 1) {
DelayK(100);
while(s7 ==0) {
stat_k = 0;
}
L1 = 1;
}
}
}
if(s6 == 0) {
DelayK(300);
if(s6 == 0) {
if(stat_k == 0) {
DelayK(100);
while(s6 == 0){
stat_k = 2;
}
L2 = 0;
DelayK(100);
}else if(stat_k == 2) {
DelayK(100);
while(s6 == 0) {
stat_k = 0;
}
L2 = 1;
}
}
}
if(s5 == 0) {
DelayK(300);
if(s5==0) {
if(stat_k == 1) {
L3 = 0;
while(s5 == 0);
L3 = 1;
}else if(stat_k == 2) {
L5 = 0;
while(s5 == 0);
L5 = 1;
}
}
}
if(s4 == 0) {
DelayK(300);
if(s4 == 0) {
if(stat_k == 1) {
L4 = 0;
while(s4 == 0);
L4 = 1;
}else if(stat_k == 2) {
L6 = 0;
while(s4 == 0);
L6 = 1;
}
}
}
}
void main(void) {
// 初始化
SystemInit();
// 先让LED使能
_74HC138(4);
while(1) {
ScanKey_Alone();
}
}