51单片机入门 - 按键驱动程序设计实验

发布者:Harmonious222最新更新时间:2022-04-22 来源: eefocus关键字:51单片机  按键驱动  高电平 手机看文章 扫描二维码
随时随地手机看文章

独立按键原理是这样的:按键没按下的时候,相应端口是高电平状态,而当按键按下的时候,相应的端口则是低电平。所以可以根据这个现象,实现相应的功能。


还有一点应该注意的是:按键在闭合和断开时,触点会存在抖动现象。

                                                    

 

在实际情况下,我们需要的是稳定闭合的那部分状态。所以可以采用延时的方法来解决这个问题,具体的过程就是先看看有没有键按下,有键按下了,再延迟一段时间,再看看有没有键按下,

这时候如果还是有键按下的话那就真的是有键按下了。


而这个抖动的时间大概是10ms,所以只要用一个延时10ms的子函数就行。


上面代码的第66行那个判断按键是否松开也是必要的,虽然在这个程序中有和没有区别不大,但是在有的程序中加入要求按键松开之后才出现什么现象之类的东西的话,那这部分就显得必要了。

/*******************************************************************************

实验名称:       8个独立按键控制8盏LED灯(按下哪个键,那个键对应的LED亮)

实验时间:        

*******************************************************************************/

#include

 

#define LED_KEY P0   //LED灯用P0口

#define IO_KEY  P1     //独立按键用P1口

 

void Delay();        //延时函数

unsigned char Key_Scan();     //获取按键值

 

void main()

{

    unsigned char Key_Value, LED_Value;

    

    while(1)

    {

        Key_Value = Key_Scan();

        switch(Key_Value)

        {

            case(0xFE):         //K1按下

                LED_Value = 0x01;

                break;

            case(0xFD):         //K2按下

                LED_Value = 0x02;

                break;

            case(0xFB):         //K3按下

                LED_Value = 0x04;

                break;

            case(0xF7):         //K4按下

                LED_Value = 0x08;

                break;

            case(0xEF):         //K5按下

                LED_Value = 0x10;

                break;

            case(0xDF):         //K6按下

                LED_Value = 0x20;

                break;

            case(0xBF):         //K7按下

                LED_Value = 0x40;

                break;

            case(0x7F):         //K8按下

                LED_Value = 0x80;

                break;

            default:

                break;

        }

        

        LED_KEY = LED_Value;  //点亮相应LED        

    }

}

 

unsigned char Key_Scan()

{

    unsigned char Key_Value,i;

 

    if(IO_KEY != 0)

    {

        Delay();            //消除抖动

 

        if(IO_KEY != 0xFF)

        {

            Key_Value = IO_KEY;

            i = 0;

            if((i<50)&&(IO_KEY != 0xFF)) //判断按键是否松开

            {

                Delay();

                i++;    

            }

        }

    }

    return Key_Value;

}

 

void Delay()              //延迟10ms

{

    unsigned char a,b,c;

 

    for(c=1;c>0;c--)

    {

        for(b=38;b>0;b--)

        {

            for(a=130;a>0;a--)

            {};

        }

    }

}


 


/*******************************************************************************

*实验名称       :按键控制LED左右移

*实验时间              

*******************************************************************************/

#include

#include

 

//--定义要使用的IO口--//

sbit      K1 = P1^0;       //对应按钮K1

sbit     K2 = P1^1;        //对应按钮K2

#define  LED_KEY P0    //LED使用P0口

 

//--定义全局函数--//

void Delay10ms(unsigned int c);   //延时10ms

unsigned char Key_Scan();

 

/*******************************************************************************

* 函 数 名         : main

* 函数功能           : 主函数

*******************************************************************************/

void main(void)

{

    unsigned char ledValue, keyNum;

 

    ledValue = 0x01;

 

    while (1)

    {    

        keyNum = Key_Scan();  //扫描键盘

 

        if (keyNum == 1)      //如果键值返回1

        {

            ledValue = _crol_(ledValue, 1);    //左循环

        }

        else if (keyNum == 2)

        {

            ledValue = _cror_(ledValue, 1);    //右循环

        }

 

        LED_KEY = ledValue;  //点亮LED灯

    }                

}

 

/*******************************************************************************

* 函 数 名                     : Key_Scan()

* 函数功能                       : 扫描键盘

*******************************************************************************/

 

unsigned char Key_Scan()

{

    unsigned char keyValue = 0 , i; //保存键值

 

    //--检测按键1--//

    if (K1==0)        //检测按键K1是否按下

    {

        Delay10ms(1);    //消除抖动

 

        if (K1==0)    //再次检测按键是否按下

        {

            keyValue = 1;

            i = 0;

            while ((i<50) && (K1==0))     //检测按键是否松开

            {

                Delay10ms(1);

                i++;

            }

        }

    }

 

    //--检测按键2--//

    if (K2==0)        //检测按键K1是否按下

    {

        Delay10ms(1);    //消除抖动

 

        if (K2==0)    //再次检测按键是否按下

        {

            keyValue = 2;

            i = 0;

            while ((i<50) && (K2==0))     //检测按键是否松开

            {

                Delay10ms(1);

                i++;

            }

        }

    }

 

    return keyValue;   //将读取到键值的值返回

}

 

/*******************************************************************************

* 函 数 名                     : Delay10ms

* 函数功能                     : 延时函数,延时10ms

*******************************************************************************/

 

void Delay10ms(unsigned int c)   //误差 0us

{

    unsigned char a, b;

 

    //--c已经在传递过来的时候已经赋值了,所以在for语句第一句就不用赋值了--//

    for (;c>0;c--)

    {

        for (b=38;b>0;b--)

        {

            for (a=130;a>0;a--);

        }

           

    }       

}


关键字:51单片机  按键驱动  高电平 引用地址:51单片机入门 - 按键驱动程序设计实验

上一篇:单片机入门 - 模电、数电与单片机
下一篇:51单片机入门 - 学习笔记

推荐阅读最新更新时间:2024-11-12 06:58

51单片机基础之外部中断(二)
代码: #include reg51.h typedef unsigned char u8; typedef unsigned int u16; sbit LED=P2^0; sbit KEY=P3^3; void delay(u16 i) { while(i--); } void EXIT1_Init(void) //外部中断初始化 { IT1=1;//跳变沿触发方式(下降沿),低电平触发 EX1=1;//打开INT0的中断允许,打开外部中断0允许 EA=1;//打开总中断 } void main(void) { EXIT1_Init();//打开外部中断 while(1)
[单片机]
采用51单片机设计的温室测试系统
  设施农业是世界现代农业发展的主要方向之一,我国农业正处于从传统也向高产、优质、高效为目的的现代化农业转化新阶段,设施农业是我国今后比较长的时间内农业发展的个主要方向。   环境控制对果树生产的重要作用已经为国内外大量的科学实验和生产的实践所证实。只有在适宜的生长环境下果疏才能充分发挥其高产潜力。多年的有关果树生长环境的研究,不仪知道了农业生产,也为温室环境测控的研究提供了理论和依据。但如何利用传感器技术,白动检测技术,通讯技术,计算机技术的发展和温室栽培的推广研制出对温室温度,湿度,二氧化碳浓度的智能测控系统,为果树提供最佳的生长环境,一直是农业研究者面临的重要课题。   虽然国外采用了全智能控制,但是他们的成本太高,不适
[单片机]
采用<font color='red'>51单片机</font>设计的温室测试系统
51单片机学习笔记(二)
按照教材,昨天学到了检测按键的程序,也很明确昨天学那个程序难登大雅之堂,因为它没有实现按键在闭合和开关时的电压信号抖动。 如图示,键按下试产生多个抖动的波形,也就是产生了多个101010,而我们实际中只是两个状态只是1,或只是0。所以收集了干扰信号。于是就有今天我学的“去抖动程序” 去抖原理:收到第一个低电平信号(按下的信号)后,开始延迟再次收集信号,再确认是否低电平(一直被按下)这时收集的信息就来自抖动波形图的中间部分,所以只要这个时间段是低电平,按键就肯定被按下了,不会再有抖动。这时就跳到指令检测这个按键引脚什么时候变为高电平(表示释放按键),不断循环检测,直至按键被释放。检测到释放信号后,就有cpl指令修改相应led灯
[单片机]
51单片机 C 语言编程:单片机定时中断
要求:P1.0输出周期为2ms的方波,P1.1输出5ms的方波,占空比都为1:1.(高低电平一样的)。 晶振频率为24MHz。(使用T0和T1两个定时计数器)汇编或C都行。 编程如下: //================================================ #include reg52.h #define uchar unsigned char #define uint unsigned int void init(); sbit P10 = P1^0; sbit P11 = P1^1; //---------------------------- main() { init(
[单片机]
用C51单片机设计远程红外安防监控管理系统
  随着社会经济的发展和科学技术的进步,人们对办公场所的安全提出了更高的要求。特别对于企业而言,防火防盗更是必不可少的安全防范事件。针对传统的安防成本比较高、且实时性不强、集中管理控制困难、难以对安全隐患问题进行排查预警等情况; 现基于单片机技术和移动通信网络开发出一种实时、无线、便于管理、成本低廉的主动防护远程红外监控管理系统。   1 系统组成及功能   1.1 系统组成   整个系统主要由现场监控端、移动传输网络和监控中心三部分组成。现场监控端包括监控主机、传感器(包括红外传感器、烟雾传感器和门磁传感器)、摄像头和GPRS 通信模块。传输网络借由移动通信的GSM\\GPRS 网络,完成远程通信。监控中心由可靠的DCN
[单片机]
用C<font color='red'>51单片机</font>设计远程红外安防监控管理系统
51单片机P2口介绍
P2.0 P2.7为P2口的8位双向口线,第一功能为基本输入/输出;第二功能是在系统扩展时作为高8位地址总线使用。 P2口内部结构及其功能描述 如图是P2口内部1位的电路结构。注意与P0结构的不同之处。 P2端口是一个准双向端口; 第一功能: 当P2端口作为通用I/O使用时,单片机控制二选一复用器倒向P2.x锁存器的Q端,此时P2端口的功能和使用方法都类似于P1端口;系统复位时,端口锁存器自动置1,输出的下拉驱动器截止,P2端口可直接作为输入口使用。 第二功能: P2端口在系统扩展外围总线时输出高8位地址,此时P2不可作为通用I/O端口使用; P2端口输出高8位地址时,硬
[单片机]
8通道自动温度检测系统仿真
仿真程序功能:用八个通道分别检测8路信号,并通过数码管实时显示 程序参考源代码如下: CLR P3.7 MAIN:MOV 38H,#00H MOV 39H,#00H MOV 3AH,#00H MOV 3BH,#00H LCALL GET_TEMPER LCALL TEMPRRO MOV P2,#06H LCALL PRO ;------------------------------------------------------ MOV 38H,#00H MOV 39H,#00H MOV 3AH,#00H MOV 3BH,#00H LCALL GET_TEMPER2 LCALL TEMPRRO M
[单片机]
8通道自动温度检测系统仿真
51单片机实现4位数以内的加减法
  中南民族大学,电子信息工程学院,开设了一门课程,叫《嵌入式电路设计》,由舒老师带头,旨在引导低年级的学生入门嵌入式,其内容比较多,包括模电、数电、C语言、单片机、EDA技术等。最近有位师弟找到我,希望我能帮他指导一下,利用AT89C52单片机设计一个最小系统,其中包括矩阵键盘、数码管显示、中断、2位数加减法、定时计数与暂停等功能。我也粗略的设计了一个,在此分享出来,希望能对初学者有所帮助,使更多的人加入到嵌入式的行业来。   开发工具:keil   仿真工具:proteus 代码如下: 头文件:inc_all.h 1 #ifndef INC_ALL_H_ 2 #define INC_ALL_H_ 3 4 volati
[单片机]

推荐帖子

[好书]像500强一样经营自己
像500强一样经营自己------一本很好的书像500强一样经营自己坐沙发看书喽,呵呵回复:像500强一样经营自己好书!谢谢楼主!!对当代大学生很有帮助啊回复:像500强一样经营自己下载了,正在看,谢谢喽回复:像500强一样经营自己谢谢,看看回复:像500强一样经营自己谢谢.楼主咯!回复:像500强一样经营自己好书!谢谢!回复:像500强一样经营自己好书.看看回复:像500强一样经营自己很有用哦回复:像500强一样经
SuperStar515 嵌入式系统
EP9315GPIO驱动在镜像中无法被加载!
为什么我写的驱动编译通过了,做成镜像后,在wince启动时,DWORDGIO_Init(DWORDdwcontext)无法被加载,反而只有DllEntry()些函数在超级终端上看得到办出输出信息!EP9315GPIO驱动在镜像中无法被加载!一般应该是你的驱动已经退出造成的,在你的dllentry函数退出部分添加打印信息验证一下!造成这种结果的可能原因是你的init函数返回值或者参数有问题那我把源码贴出,请帮忙看看啊,各位高手!#includewindows.h#in
lvtian2 嵌入式系统
5G 手机的发射功率,到底能有多大?
随着5G网络的建设,5G基站成本高,尤其是能耗大的问题已广为人知。以中国移动为例,为了下行支持高速率,其2.6GHz的射频模块就要求64通道,最大320瓦发射功率。而与基站通信的5G手机,由于和人体的接触过于密切,「辐射危害」的底线必须严防死守,因此只能戴着镣铐起舞,发射功率严格受限。4G手机的发射功率,就被协议限制为最大23dBm(0.2瓦),这个功率虽说不大,但4G的主流频段(FDD1800MHz)频率较低,传播损耗相对较小,用起来倒也问题不大
zqy1111 RF/无线
关于无线通信不同应用中,通信层协议的问题求助!
各位大神,本人主要是做应用层设计开发的。暂时没有打算直接对无线低层芯片进行开发。计划采购现成的无线模块(UHF、Zigbee、Lora等),配合自家的采集模块,构成无线传感网的不同应用。现在的问题就是,有线传感网的软件层协议通常有的选择,如标准的(485-ModbusRTU协议)、SDI-12协议,属于应答模式。当实现无线传感网应用时,如果沿用上面两种协议有个缺点就是传感端必须保持常供电,实时等待主站端发过来的命令,这在户外应用要求低功耗的情况下显然不行。如果考虑到低功耗问题,比较好的方式
yunyinliu RF/无线
Zynq-7000应用处理单元(转)
转自http://www.ituring.com.cn/tupubarticle/3348Zynq-7000应用处理单元是该器件最重要的功能单元。只有掌握了应用处理单元的结构原理,才能高效地实现基于Zynq-7000的嵌入式系统设计。3.1 应用处理单元应用处理单元(ApplicationProcessingUnit,APU)存在于PS内,包含带有NEON协处理器的两个Cortex-A9处理器。在多处理器配置中,将两个处理器连接起来共享一个512KBL2高速缓存。每个处理器是
白丁 FPGA/CPLD
Altium Designer 24.9.1 版
新功能说明 版本发布说明AltiumDesigner24.9.1版哈哈,还没有用,我打算先用一下,感觉AD还是蛮简单的,但是也就是小厂用用 使用AD的工程师很多 看一下千古更新帝啊,更新频率真快!不知改善了什么,又带出什么新BUG看看版本发布说明的是什么发的是什么?看看学习学习更新的好快呀。。。。。。。。。。。。。。。。是干事业的样子。更新的好快呀。。。。。。。。。。。。软件能下载吗?
dcexpert PCB设计
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved