www.openedv.com
您好,欢迎您!    会员注册 | 登入 
公告:欢迎访问www.openedv.com开源电子网,开源共享共同进步,祝您新年快乐,万事如意!
设为首页 | 加入收藏
论坛首页 » 51单片机 前往: 
一个按键两种功能的问题
发表人 内容
[Down] [Up]
[楼主位] kyng

等级:NO
注册时间:
2011/10/11 19:53
文章: 10
离线

我做了一个一个按键两种功能的程序,就是一按短时间就亮小灯,长按就亮大灯的程序,但时序时候好困难,希望帮手看看!!!

#include<pic.h>
#include "ET18F11.h"
__CONFIG(0X3044);


#define uchar unsigned char
#define uint unsigned int
uint num,num1;
 bit duan_flag,chang_flag1;
 
void delay(uint n)
{
 uint i,j;
 for(i=n;i>0;i--)
 for(j=110;j>0;j--);
 


}

void init_com()
{
 OPTION=0X00;
 WPUA2=1;
 TRISA=0XFF;
 TRISC=0X00;
 PORTA=0X00;
 PORTC=0X00; //初始化必须置零。
    //TMR0=0X06;
    //T0IE=0;
    //T0IF=0;
    //OPTION=0X02;
    GIE=1;
    INTCON=0XC0;
    //PIE1=0X01;
    //TMR1H=(65536-50000)/256;
    //TMR1L=(65536-50000)%256;
    //T1CON=0X01;
}

   void  scankey()
   {
    if(RA2==0)
    {
     delay(10);
    num++;
     if(num<200)
    {
    duan_flag=1;
   
   
    if(num>200)
    {
    
        chang_flag1=1;
        duan_flag=0;
  
     
   
    }
   
   
   
   
   
    }
   
  }
  else if(RA2==1)
 
  {
   num=0;
   if(duan_flag==1)
   {
    duan_flag=1;
   
  
  
   }
 
 
 
 
 
  }
 
  }
  
void display()
{
 if(chang_flag1==1)
 {
  
  RC1=!RC1;
  chang_flag1=0;
  duan_flag=0;
 
 
 
 }
 if(duan_flag==1)
 {
  
     while(RA2==1)
     {
  RC6=!RC6;
  RC7=!RC7;
  duan_flag=0;
     chang_flag1=0;
     }
 
 
 }

 

 


}
  
  
  
  


   
  
  
  
  
  
  
  
 
 
 
 

 
   
   
                   
    

 
 
   void main()
   {
    init_com();
    while(1)
    {
    scankey();
    display();
  
 
  
  
   }
  
   }
  
  /* void interrupt timer0()
{
 if(TMR1IF=1)
 
    TMR1IF=0;
    
    TMR1H=(65536-50000)/256;
    TMR1L=(65536-50000)%256;
   
    num++;
 
   
  
  
   
  
 
 } */
   

 


 



[加为好友] 回复 引用回复
[Down] [Up]
[1楼] 正点原子


等级:NO
注册时间:
2010/12/02 10:41
文章: 8097
来自: 湖南
在线

回复【楼主位】 kyng :
---------------------------------
设计个局部静态变量,利用延时,并记录下进入的次数就可以判断是长按还是短按了。



我的淘宝小店:http://shop62103354.taobao.com
[加为好友] 回复 引用回复
[Down] [Up]
[2楼] wolfdong7

等级:NO
注册时间:
2010/12/19 20:18
文章: 208
来自: 湖南
离线

在定时器中,设置好进入定时的时间,在中断中

/*********************************************************************************************************
** 函数名称: key_driver
** 功能描述: 按键状态机,可以实现消抖、短按、长按
**
** 输 入: 无
**
** 输 出: 无
**        
** 全局变量: 无

** 修改人: 程铭栋
** 日 期: 2011年10月10日
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
unsigned char key_driver(void) 

    static unsigned char key_state = key_state_0, key_time = 0; 
    unsigned char key_press, key_return = N_key; 

    key_press = key_input;                    // 读按键I/O电平 

    switch (key_state) 
    { 
       case key_state_0:                              // 按键初始态 
        if (key_press) key_state = key_state_1;      // 键被按下,状态转换到按键消抖和确认状态 
        break; 
       
       case key_state_1:                      // 按键消抖与确认态 
        if (key_press) 
        { 
             key_time = 0;                   //  
             key_state = key_state_2;   // 按键仍然处于按下,消抖完成,状态转换到按下键时间的计时状态,但返回的还是无键事件 
        } 
        else 
             key_state = key_state_0;   // 按键已抬起,转换到按键初始态。此处完成和实现软件消抖,其实按键的按下和释放都在此消抖的。 
        break; 
       
       case key_state_2: 
        if(!key_press) 
        { 
             key_return = S_key;        // 此时按键释放,说明是产生一次短操作,回送S_key 
             key_state = key_state_0;   // 转换到按键初始态 
        } 
        else if (++key_time >= 10)     // 继续按下,计时加10ms(10ms为本函数循环执行间隔) 
        { 
             key_return = L_key;        // 按下时间>1000ms,此按键为长按操作,返回长键事件 
             key_state = key_state_3;   // 转换到等待按键释放状态 
        } 
        break; 

       case key_state_3:                 // 等待按键释放状态,此状态只返回无按键事件 
        if (!key_press) key_state = key_state_0; //按键已释放,转换到按键初始态 
        break; 
    } 
    return key_return; 
}

/*********************************************************************************************************
** 函数名称: key_read
** 功能描述: 先根据key_driver的状态指示,再根据按键的状态,确定到底是不按、短按、双击、长按
**
** 输 入: key_driver
**
** 输 出: 无
**        
** 全局变量: 无

** 修改人: 程铭栋
** 日 期: 2011年10月10日
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
unsigned char key_read(void) 

    static unsigned char key_m = key_state_0, key_time_1 = 0; 
    unsigned char key_return = N_key,key_temp; 
     
    key_temp = key_driver(); 
     
    switch(key_m) 
    { 
         case key_state_0: 
         if (key_temp == S_key ) 
            { 
                 key_time_1 = 0;               // 第1次单击,不返回,到下个状态判断后面是否出现双击 
                 key_m = key_state_1; 
            } 
            else 
                 key_return = key_temp;        // 对于无键、长键,返回原事件 
            break; 

         case key_state_1: 
            if (key_temp == S_key)             // 又一次单击(间隔肯定<500ms) 
            { 
                 key_return = D_key;           // 返回双击键事件,回初始状态 
                 key_m = key_state_0; 
            } 
            else                                
            {                                  // 这里500ms内肯定读到的都是无键事件,因为长键>1000ms,在1s前低层返回的都是无键 
                 if(++key_time_1 >= 5) 
                 { 
                      key_return = S_key;      // 500ms内没有再次出现单键事件,返回上一次的单键事件 
                      key_m = key_state_0;     // 返回初始状态 
                 } 
             } 
             break; 
    }
    return key_return; 
}




虽然我不属牛,但是我还是希望某一天能够像正点原子一样牛!
[加为好友] 回复 引用回复
[Down] [Up]
[3楼] wolfdong7

等级:NO
注册时间:
2010/12/19 20:18
文章: 208
来自: 湖南
离线

下面是我STM32的源程序。
我的板子不是原子的MINISTM32板子,所以你需要修改下管脚配置。




虽然我不属牛,但是我还是希望某一天能够像正点原子一样牛!
[加为好友] 回复 引用回复
[Down] [Up]
[4楼] kyng

等级:NO
注册时间:
2011/10/11 19:53
文章: 10
离线

我还是没有搞懂,最好在我原来的地方上改好!!!我用的是PIC的!!



[加为好友] 回复 引用回复
[Down] [Up]
[5楼] kyng

等级:NO
注册时间:
2011/10/11 19:53
文章: 10
离线

为什么要静态变量???



[加为好友] 回复 引用回复
[Down] [Up]
[6楼] 正点原子


等级:NO
注册时间:
2010/12/02 10:41
文章: 8097
来自: 湖南
在线

回复【5楼】 kyng :
---------------------------------
自己想一下.



我的淘宝小店:http://shop62103354.taobao.com
[加为好友] 回复 引用回复
[Down] [Up]
[7楼] wolfdong7

等级:NO
注册时间:
2010/12/19 20:18
文章: 208
来自: 湖南
离线

回复【4楼】 kyng :
---------------------------------
大哥,我都大部分注释了。

你认真的耐心的看下,应该很简单的。



虽然我不属牛,但是我还是希望某一天能够像正点原子一样牛!
[加为好友] 回复 引用回复
 
前往: 

Powered by ALIENTEK工作室 © 粤ICP备12000418号-1