程序运行结果很怪!求救啊!

2020-01-24 12:02发布

本帖最后由 牛东 于 2014-3-21 12:11 编辑

结果是每次上电第一次按key_1,程序是按照设计的运行:消抖,先亮一盏,延时1秒两盏,再延时1秒亮三盏,松手全灭。
可是松手后第二次怎么按Key_1程序都没反应,要过几分钟或重新上电复位才行!!!晕啊!!搞了很久没搞定!!

#include <reg52.h>
#include "MacroAndConst.h"
#include "Timer.h"
#include "KeyProg.h"

void main(void)
{               
        uint8 KeyValue = KEY_NULL;
        KeyInit() ;
        Timer0Init();
        EA = 1;
        P0=0xff;

        while(1)
        {        
                GetKey(&KeyValue);
                if(KeyValue == (KEY_VALUE_1 | KEY_DOWN)) P0 = 0xfe;
                if(KeyValue == (KEY_VALUE_1 | KEY_LONG)) P0 = 0xfc;
                if(KeyValue == (KEY_VALUE_1 | KEY_CONTINUE)) P0 = 0xf8;
                if(KeyValue == (KEY_VALUE_1 | KEY_UP)) P0 = 0xf0;
                if(KeyValue ==KEY_NULL) P0=0xff;
        }
}



/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
#include <reg52.h>
#include "MacroAndConst.h"
#include "Timer.h"

#define KEY_VALUE_1 0x0e  //确定哪个键按下,键值
#define KEY_VALUE_2 0x0d
#define KEY_VALUE_3 0x0b
#define KEY_VALUE_4 0x07
#define KEY_NULL         0x0f

sbit io_key_1 = P3^0 ;
sbit io_key_2 = P3^1 ;
sbit io_key_3 = P3^2 ;
sbit io_key_4 = P3^3 ;

void KeyInit(void)
{
        io_key_1 = 1 ;
        io_key_2 = 1 ;
        io_key_3 = 1 ;
        io_key_4 = 1 ;
}

static uint8 KeyScan(void) //确定哪个键按下,键值
{
        if(io_key_1 == 0)return KEY_VALUE_1 ;
        if(io_key_2 == 0)return KEY_VALUE_2 ;
        if(io_key_3 == 0)return KEY_VALUE_3 ;
        if(io_key_4 == 0)return KEY_VALUE_4 ;
        return KEY_NULL ;
}


//定义按键返回值状态(按下,长按,连发,释放)
#define KEY_DOWN 0x80
#define KEY_LONG 0x40
#define KEY_CONTINUE 0x20
#define KEY_UP 0x10


//定义按键状态
#define KEY_STATE_INIT 0
#define KEY_STATE_WOBBLE 1
#define KEY_STATE_PRESS 2
#define KEY_STATE_LONG 3
#define KEY_STATE_CONTINUE 4
#define KEY_STATE_RELEASE 5

void GetKey(uint8 *pKeyValue)

{
        static uint8  s_u8KeyState =KEY_STATE_INIT ;
        static uint16 s_u8KeyTimeCount = 0;            //按键时间计数器
        static uint8  s_u8LastKey = KEY_NULL ;         //保存按键释放时候的键值
        uint8 KeyTemp = KEY_NULL ;

        KeyTemp =KeyScan() ;      

        switch(s_u8KeyState)
        {
                case KEY_STATE_INIT :
                {
                        if(KEY_NULL != (KeyTemp))
                        {
                                s_u8KeyState = KEY_STATE_WOBBLE ;
                        }
                }
                break ;
               
                case KEY_STATE_WOBBLE : //消抖
                {
                        if(g_bSystemTime1Ms ) //系统1mS时标到
                        {
                                g_bSystemTime1Ms = 0 ;
                                s_u8KeyTimeCount++;
                                if(s_u8KeyTimeCount==10)
                                {        
                                        s_u8KeyTimeCount=0;               
                                        s_u8KeyState = KEY_STATE_PRESS ;
                                }                                
                        }
                }
                break ;

                case KEY_STATE_PRESS :
                {
                        if(KEY_NULL != (KeyTemp))               
                        {
                                s_u8LastKey = KeyTemp ;                 //保存键值,以便在释放按键状态返回键值
                                KeyTemp |= KEY_DOWN ;                         //按键按下
                                s_u8KeyState = KEY_STATE_LONG ;
                        }
                        else
                        {
                                s_u8KeyState = KEY_STATE_INIT ;
                        }
                }
                break ;

                case KEY_STATE_LONG :
                {
                        if(KEY_NULL != (KeyTemp))
                        {
                                if(g_bSystemTime1Ms )        //系统1mS时标到
                                {
                                        g_bSystemTime1Ms =0;        
                                        s_u8KeyTimeCount++;
                                        if(s_u8KeyTimeCount==1000)
                                        {
                                                s_u8KeyTimeCount=0;
                                                KeyTemp |= KEY_LONG ;         //长按键事件发生
                                                s_u8KeyState = KEY_STATE_CONTINUE ;
                                        }
                                }
                        }
                        else
                        {
                                s_u8KeyState = KEY_STATE_RELEASE ;
                        }
                }
                break ;


                case KEY_STATE_CONTINUE :
                {
                        if(KEY_NULL != (KeyTemp))
                        {
                                if(g_bSystemTime1Ms )        //系统1mS时标到
                                {
                                        g_bSystemTime1Ms =0;        
                                        s_u8KeyTimeCount++;
                                        if(s_u8KeyTimeCount==1000)
                                        {
                                                s_u8KeyTimeCount=0;
                                                KeyTemp |= KEY_CONTINUE ;
                                        }
                                }
                        }
                        else
                        {
                                s_u8KeyState = KEY_STATE_RELEASE ;
                        }
                }
                break ;


                case KEY_STATE_RELEASE :
                {
                        s_u8LastKey |= KEY_UP ;
                        KeyTemp = s_u8LastKey ;
                        s_u8KeyState = KEY_STATE_INIT ;
                }
                break ;

                default : break ;
        }
        
        *pKeyValue = KeyTemp ; //返回键值
}


//////////////////////////////////////////////////////////////////////////////////////////////////
#include<reg52.h>
#include "MacroAndConst.h"
bit  g_bSystemTime1Ms = 0 ;  // 1MS系统时标
void Timer0Init(void)
{
    TMOD &= 0xf0 ;
    TMOD |= 0x01 ;      //定时器0工作方式1
    TH0  =  0xfc ;      //定时器初始值1MS
    TL0  =  0x66 ;
    TR0  = 1 ;
    ET0  = 1 ;
}

void Time0Isr(void) interrupt 1
{
    TH0  =  0xfc ;            //定时器重新赋初值1MS
    TL0  =  0x66 ;
    g_bSystemTime1Ms = 1 ;    //1MS时标标志位置位
}





友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
该问题目前已经被作者或者管理员关闭, 无法添加新回复
8条回答
牛东
1楼-- · 2020-01-25 08:18
lcw_swust 发表于 2014-3-21 10:08
大概看了下,可能是s_u8KeyTimeCount导致,
例如这句:if(s_u8KeyTimeCount==10),有可能s_u8KeyTimeCount已经 ...

再问一下!!我用定时器延时的方式可行吗??
lcw_swust
2楼-- · 2020-01-25 13:10
 精彩回答 2  元偷偷看……

一周热门 更多>