bios 发表于 2019-9-26 09:27:18

请教单片机这样检测键盘,能正常工作吗

我做的时钟的主程序是这样的

while(1)
{
keydriver();
display();
settime();
}

主程序的主循环中,三个函数分别是键盘检测程序,动态扫描程序和时间设置程序。
程序首先执行键盘扫描程序,请教大家,如果有按键按下,也被正常识别了,等到执行settime时间调节程序时,那个按键按下的状态,还能起作用吗?
这样的整体思路,程序能正常工作吗?

矿坛铁粉 发表于 2019-9-26 09:35:20

baofu 发表于 2019-9-26 10:48:51

没有代码,不好说。如果按你的思路,先扫描键盘,到 settime()中你如何知道键盘状态?如果再检测一次,那前面扫描有什么用?
所以从原理上说,每次扫描键盘函数时,用一个变量储存扫描结果,啥时候用,就取这个结果用。

raysin 发表于 2019-9-26 10:51:09

理论上可以, 只要不互相干扰, 全域变数 正确使用的话

xyz543 发表于 2019-9-26 12:00:29

楼主的代码我换句话来说:我家的冰箱坏了,请问是哪一个部分坏了?是啥原因造成故障的?差不多就是这样!...

bios 发表于 2019-9-26 12:19:27

baofu 发表于 2019-9-26 10:48
没有代码,不好说。如果按你的思路,先扫描键盘,到 settime()中你如何知道键盘状态?如果再检测一次,那前 ...

谢谢指点
用一个变量存储按键状态的话,如果程序中还有循环,会不会造成多次按键-连发的效果?

shzps 发表于 2019-9-26 14:55:04

代码就跟人脑一样,把可能出现的问题都罗列出来就ok了

baofu 发表于 2019-9-26 17:38:41

bios 发表于 2019-9-26 12:19
谢谢指点
用一个变量存储按键状态的话,如果程序中还有循环,会不会造成多次按键-连发的效果?

连发与否,就看你在程序中如何处理了,与按键无关吧?

清风碧雪 发表于 2019-9-26 18:19:35

如果是这样编写程序,数码管扫描显示和要修改的数据程序部分另行编写,按键按下时调用相应的程序块就可以了,退出按键程序时,又回到程序主循环中。

fshwen 发表于 2019-9-28 12:03:29

bios 发表于 2019-9-26 12:19
谢谢指点
用一个变量存储按键状态的话,如果程序中还有循环,会不会造成多次按键-连发的效果?

做过类似的,是用状态位来判断的,如果在按键按下,程序判断如果是第一次,则执行按键的操作,否则跳过

isoimg2130 发表于 2019-9-30 10:20:46

可以,我实际用过。
while(1)
{
键盘扫描();(定义一个变量,如果按键1按下,这个变量为1,如果2按下为2.以此类推)
调节();(读取那个按键变量,如果为1,调节一次,然后置零,从此不再触发,除非再次按下。以此类推)
显示();
}

w6955 发表于 2019-9-30 12:37:47

本帖最后由 w6955 于 2019-9-30 12:38 编辑

看了几次没看明白,键盘软件设定是这样的:发现按下,计时,计时结束再次检测,如果仍然有效,那么本次按键有效,等待按键释放后再进入按键子程序来处理,长时间按下,只要不释放绝不会再次进入。为应对较复杂情况,按键触发中断是个好办法。

zhxzhx 发表于 2019-10-1 16:12:08

别听他们瞎说,利用变量传递信息,可以的,这个是状态机的一个极端特例

夏国特 发表于 2019-10-10 17:00:53

可以的,按键处理程序负责时间横向滤波消除抖动,然后获取键值以及键值序列、前向差分、后向差分生成按下和释放动作事件,通过全同判定和计数获取长按状态。
后面的程序只要读取状态、事件标志变量就可以了。有个要求就是必须像你的程序这样,做成同步处理的结构,而且最好通过选通开关等待系统滴答做精确的工作周期定时,就类似与PLC的端口扫描了。要求是所有程序必须在一个滴答周期内执行完成,否则影响定时准确性。
规模不大的单片机程序(不超过1000行代码),在不需要使用实时系统的时候我都是这么做的,很准确很稳定。配合状态机使用非常棒。

夏国特 发表于 2019-10-10 17:06:45

读端口->进端口缓冲队列->全同滤波->生成按键状态、前按键状态->生成按下事件、释放事件、长按计数处理->长按判定程序(带长按判定时间做参数)、键值、事件读取程序。

周期调用它,随便多少个按键,处理都是一样,超级方便。
页: [1]
查看完整版本: 请教单片机这样检测键盘,能正常工作吗