以键扫描及动态显示刷新为例:
如果将KeyScan()及Dispay()按顺序植入到TMR0中,对于其他中断服务程序是"非人道"的一件事情. 所以,一般与张工的11.4 C框架基本雷同.
但对于我们这些"中断追星族"来说看来是件"难事".(至少不想改掉此恶习)
以8键8LED为例: 动态显示刷新频率一般定在50Hz即20mS较好,而键抖动的消抖时间恰好也在20mS左右.这样想来,KeyScan()及Dispay()真是天公做媒的一对"新人"...
如果将TMR0的定时时间设为20mS/键盘个数,即20/8=2.5mS中断一次. 每次TMR0中断时,其进入次数计数器CNT_TMR0都+1.(CNT_TMR0只取低3位)
那么,一个"美妙的事情"发生了--键盘消抖时间被蒸发了...
原来,由于采用20mS/键盘个数,每次中断只依次扫描一个键,等全部扫描完时及某键20mS到时,某次键2次的扫描间隔恰好就是20mS. 这样原本需要键盘消抖等待的20mS就让个了其他的7个键用于扫描.
那么,其键盘号即为TMR0的计数值CNT_TMR0.也省去了键值寄存器. 若每键再设一个压键次数计数器KeyCnt[n]. 若KeyCnt[CNT_TMR0]=0表示某键没压下或键释放,KeyCnt[CNT_TMR0]=2时表示键刚发生压键事件,当KeyCnt[CNT_TMR0]>=长压键时间/2.5mS时,表示有长压键事件发生.
用这种方式做出来的键手感很好,没有误动作... 而且键扫描时间基本上是原来KeyScan()函数的1/n.
再论动态显示刷新问题. 同理,动态显示刷新时间为20mS/动态显示刷新位. 故动态显示刷新位也就是TMR0的计数值CNT_TMR0. 这样显示缓冲区LedBuff[]显示某位时,显示值即为LedBuff[CNT_TMR0].
就到这里,让张工见笑了...
|
|
文章评论(0条评论)
登录后参与讨论