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

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条回答
lcw_swust
1楼-- · 2020-01-24 16:10
大概看了下,可能是s_u8KeyTimeCount导致,
例如这句:if(s_u8KeyTimeCount==10),有可能s_u8KeyTimeCount已经大于10,要让它一直加然后溢出变为0再加到10,这个时间就很长了.
建议:
1、s_u8KeyState改变时,加上s_u8KeyTimeCount=0,例如在s_u8KeyState = KEY_STATE_WOBBLE这句之前应该加上。
2、if语句里不要写成==,尺量用>=。
zjk
2楼-- · 2020-01-24 17:25
本帖最后由 zjk 于 2014-3-21 11:42 编辑

汗,感觉应该是“uint8 KeyValue = KEY_NULL;”放置的位置问题,LZ只在初始化里放置了“uint8 KeyValue = KEY_NULL;”,这样应该只执行一次的吧,感觉应该把“KeyValue = KEY_NULL;”放到while语句里去,写成这样应该可以吧。
      
        uint8 KeyValue;
        while(1)
        {      
                KeyValue = KEY_NULL;
                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 = 0xff;
        }
}
牛东
3楼-- · 2020-01-24 23:04
 精彩回答 2  元偷偷看……
牛东
4楼-- · 2020-01-25 02:41
本帖最后由 牛东 于 2014-3-21 12:39 编辑
lcw_swust 发表于 2014-3-21 11:56
大概看了下,可能是s_u8KeyTimeCount导致,
例如这句:if(s_u8KeyTimeCount==10),有可能s_u8KeyTimeCount已经 ...


哥,把==改为>=就可以啦!!泪牛满面啊!!!!!
jswd0810
5楼-- · 2020-01-25 05:25
static uint8 KeyScan(void) //确定哪个键按下,键值
{
        if(io_key_1 == 0)return KEY_VALUE_1 ;
        else if(io_key_2 == 0)return KEY_VALUE_2 ;
        else if(io_key_3 == 0)return KEY_VALUE_3 ;
        else if(io_key_4 == 0)return KEY_VALUE_4 ;
        return KEY_NULL ;
}
这样改改试试
牛东
6楼-- · 2020-01-25 06:38
jswd0810 发表于 2014-3-21 12:21
static uint8 KeyScan(void) //确定哪个键按下,键值
{
        if(io_key_1 == 0)return KEY_VALUE_1 ;


把==改为>=就可以啦!!谢谢

一周热门 更多>