找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1679|回复: 3
收起左侧

case key_s3 : 怎么实现长短按?

[复制链接]
ID:358998 发表于 2018-7-5 10:00 | 显示全部楼层 |阅读模式

按键有效,判断即将进入case 1:

按键有效,判断即将进入case 1:

没有进入case:1 直接跳出switch

没有进入case:1  直接跳出switch

  1. #include "BS87D20A-3.h"
  2. #define com1    _pc1
  3. #define com2        _pc0
  4. #define com3        _pc2
  5. #define com4        _pc3
  6. #define key1    _pd2
  7. #define key2        _pd3
  8. #define key3        _pa1
  9. #define key4    _pa4
  10. //#define key_state_0     0   //按键的初始状态
  11. //#define key_state_1     1   //按键按下的状态
  12. //#define key_state_2     2   //按键释放的状态
  13. volatile bit Flag_T5ms;
  14. volatile bit Flag_T10ms;
  15. volatile bit Flag_T1s;

  16. const unsigned char tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};
  17. unsigned char strtab[3];//缓冲区
  18. unsigned char key_number=0;

  19. unsigned char sec=0,min=0,hour=0;
  20. unsigned char temp;
  21. unsigned long s;  //秒级
  22. unsigned long ms10;//毫秒
  23. unsigned long ms5;
  24. unsigned char n;

  25. enum key_states_e{  
  26.     key_s1,  
  27.     key_s2,  
  28.     key_s3,  
  29.     key_s4  
  30. };
  31. void read_key()
  32. {
  33.         static enum key_states_e key_state=key_s1;
  34. //        static char key_state;
  35.         static int press=0;
  36.         unsigned char key_press;       //按键是否被按下
  37.          //key_state=0;     //按键的状态
  38.     key_press=key1;         // 读按键I/O电

  39.     switch (key_state)
  40.     {
  41.         case key_s1:                 // 按键初始态
  42.                 if (!key_press)
  43.                         {        
  44.                                 key_state=key_s2; // 键被按下,状态转换到键确认态
  45.                                 
  46.                 }
  47.                 else key_state=key_s1;
  48.                         break;
  49.                                        
  50.         case key_s2:                  // 按键确认态
  51.             if (!key_press)
  52.             {
  53.                             key_state=key_s3;            
  54.             }
  55.             else
  56.             {
  57.                                 key_state=key_s1; // 按键已抬起,转换到按键初始态
  58.                         }
  59.             break;
  60.                                 
  61.         case key_s3:
  62.             if (!key_press)
  63.                         {
  64.                                 key_state=key_s3;//按键确认按下状态  
  65.                                 
  66.                           com4=~com4;
  67.                            _pb=tab[2];

  68.             }
  69.             else
  70.             {
  71.                     key_state=key_s1;
  72.             }
  73.                 case key_s4:
  74.                         if(key_press)
  75.                         {
  76.                                 key_state=key_s1;
  77.                                 }
  78.             break;
  79.         default: key_state=key_s1; press=0; break;
  80.    }
  81. }

  82. void displaypro()
  83. {
  84.         strtab[0]=tab[sec%10];
  85.         strtab[1]=tab[sec/10];
  86.         strtab[2]=tab[min%10];
  87.         strtab[3]=tab[min/10];

  88. }
  89. void display_drive()
  90. {
  91.         com1=1;com2=1;com3=1;com4=1;
  92.                     switch(temp)
  93.                 {
  94.                         case 0:com4=0;
  95.                          _pb=strtab[temp]; break;
  96.                         case 1:com3=0;
  97.                          _pb=strtab[temp]; break;
  98.                         case 2:com2=0;
  99.                          _pb=strtab[temp]; break;
  100.                         case 3:com1=0;
  101.                          _pb=strtab[temp]; break;
  102.                         default:break;
  103.                 }
  104.                 temp++;
  105.                 if(temp==4)
  106.                         temp=0;

  107. }
  108. void init()
  109. {
  110.     _ctm0c0=0x20;  // fh/16   2us         
  111.         _ctm0c1=0xc1; // 定时/计数器模式 比较器a
  112.         _ctm0al=0xf4; // 1ms
  113.     _ctm0ah=0x01;
  114.         
  115.          _pbc=0; //输出
  116.          _pcc0=0;
  117.          _pcc1=0;
  118.          _pcc2=0;
  119.          _pcc3=0;
  120.          
  121.          _pac1=1;
  122.          _pac4=1;
  123.          _pdc2=1;
  124.          _pdc3=1;
  125.          _pdpu3=1;
  126.         _pdpu2=1;
  127.         _papu1=1;
  128.         _papu4=1;

  129.         s=1000;
  130.         ms10=10;
  131.         ms5=5;
  132.         temp=0;

  133.         n=0;
  134.         _mfe=1; //开多功能中断
  135.     _ctm0ae=1; //CTM a中断使能
  136.         _emi=1;        //开总中断
  137.         _ct0on=1; //开定时器
  138.              com1=1;com2=1;com3=1;
  139.                 com4=1;
  140.         }
  141.         void main()
  142.         {
  143.                 init();
  144.                 while(1)
  145.                 {
  146.         
  147.                         if(Flag_T5ms)
  148.                         {
  149.                                 Flag_T5ms=0;  
  150.                                 
  151.                         }
  152.                         if(Flag_T1s)
  153.                         {
  154.                                 Flag_T1s=0;
  155.                                 //displaypro();
  156.                                 }
  157.                         
  158.                         if(Flag_T10ms)  //10MS进入一次
  159.                         {
  160.                                 Flag_T10ms=0;  
  161.                                 read_key();

  162.                         }
  163.                         
  164.                         GCC_CLRWDT();
  165.                 }
  166.         }
  167.         
  168.         void __attribute__((interrupt(0x14))) ISR_CTMO(void)
  169.         {
  170.                 _ctm0af=0;

  171.                 s--;
  172.                 ms5--;
  173.                 ms10--;        
  174.                   if(! ms5)
  175.                 {   
  176.                         ms5=5;//5MS 视觉暂留
  177.                         Flag_T5ms=1;
  178.                         
  179.                 }        
  180.                 if(!ms10)
  181.                 {
  182.                         ms10=10;
  183.                         Flag_T10ms=1;
  184.                 }

  185.                 if(! s)
  186.                 {   
  187.                         Flag_T1s=1;
  188.                         s=1000;//1s电子钟计数
  189.                         sec++;        
  190.                 if(sec==60)
  191.                 {
  192.                sec=0;
  193.                min++;
  194.                if(min==60)
  195.                {
  196.                 min=0;
  197.                  hour++;
  198.                 if(hour==24)
  199.                 {
  200.                   hour=0;
  201.                 }
  202.                }
  203.                }
  204.                 }
  205.         }
复制代码
回复

使用道具 举报

ID:358998 发表于 2018-7-5 12:51 | 显示全部楼层
本帖最后由 zzffw 于 2018-7-5 12:56 编辑

静静等待
回复

使用道具 举报

ID:358998 发表于 2018-7-5 15:26 | 显示全部楼层
调整后



#include "BS87D20A-3.h"
#define com1    _pc1
#define com2        _pc0
#define com3        _pc2
#define com4        _pc3
#define key1    _pd2
#define key2        _pd3
#define key3        _pa1
#define key4    _pa4
//#define key_state_0     0   //按键的初始状态
//#define key_state_1     1   //按键按下的状态
//#define key_state_2     2   //按键释放的状态
volatile bit Flag_T1ms;
volatile bit Flag_T10ms;
volatile bit flag_cont;
volatile bit flag_trg;
static int key_10ms=0;
const unsigned char tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};
unsigned char strtab[3];//缓冲区
unsigned char key_number=0;

unsigned char sec=0,min=0,hour=0;
unsigned char temp;
unsigned long s;  //秒级
unsigned long ms10;//毫秒
unsigned long ms5;
unsigned char n;

enum key_states_e{  
    key_s1,  
    key_s2,  
    key_s3,  
    key_s4  
};
void read_key()
{
        static enum key_states_e key_state=key_s1;
//        static char key_state;
        static int press_10ms=0;
        static int press=100;
        unsigned char key_press;       //按键是否被按下
        //key_state=0;     //按键的状态
    key_press=key1;         // 读按键I/O电

    switch (key_state)
    {
        case key_s1:                 // 按键初始态
                if (!key_press)
                        {       
                                flag_cont=0;
                                flag_trg=0;
                                press_10ms=0;
                                key_state=key_s2; // 键被按下,状态转换到键确认态
                               
                }
                else key_state=key_s1;
                        break;
                                       
        case key_s2:                  // 按键确认态
            if (!key_press)
            {
                   
                    key_state=key_s3;
   
            }
            else
            {
                                key_state=key_s1; // 按键已抬起,转换到按键初始态
                        }
            break;
                               
        case key_s3:
            if (!key_press)
                        {
                                key_state=key_s3;//按键确认按下状态  
               
                                press_10ms++;
                                if(press_10ms>100)
                          {
                                  flag_trg=0;
                                  flag_cont=1;
                                  if(flag_cont)
                                  {       
                                         
                                          com3=0;       
                                          press--;
                                          if(!press)
                                          {
                                          press=100;
                                          _pb=tab[n++];
                                          if(n>9)
                                          n=0;
                                          }
                                  }
                           }
                                if(press_10ms>10)
                                {
                                        flag_cont=0;
                                        flag_trg=1;
                        /*                if(flag_trg)
                                        {
                                                com2=~com2;
                                                _pb=tab[2];
                                        }*/
                               
                                }


            }
            else
            {
                    key_state=key_s1;
            }
                case key_s4:
                        if(key_press)
                        {
                                if(n>9)
                          {n=0;}
                                _pb=tab[n];
                        //        com3=1;
                                flag_trg=0;
                                flag_cont=0;
                                press_10ms=0;
                                key_state=key_s1;
                                }
            break;
        default: key_state=key_s1; press_10ms=0;flag_cont=0; break;
   }
}

void displaypro()
{
        strtab[0]=tab[sec%10];
        strtab[1]=tab[sec/10];
        strtab[2]=tab[min%10];
        strtab[3]=tab[min/10];

}
void display_drive()
{
        com1=1;com2=1;com3=1;com4=1;
                    switch(temp)
                {
                        case 0:com4=0;
                         _pb=strtab[temp]; break;
                        case 1:com3=0;
                         _pb=strtab[temp]; break;
                        case 2:com2=0;
                         _pb=strtab[temp]; break;
                        case 3:com1=0;
                         _pb=strtab[temp]; break;
                        default:break;
                }
                temp++;
                if(temp==4)
                        temp=0;

}
void init()
{
    _ctm0c0=0x20;  // fh/16   2us        
        _ctm0c1=0xc1; // 定时/计数器模式 比较器a
        _ctm0al=0xf4; // 1ms
    _ctm0ah=0x01;
       
        _pbc=0; //输出
        _pcc0=0;
        _pcc1=0;
        _pcc2=0;
        _pcc3=0;
       
        _pac1=1;
        _pac4=1;
        _pdc2=1;
        _pdc3=1;
        _pdpu3=1;
        _pdpu2=1;
        _papu1=1;
        _papu4=1;

        s=1000;
        ms10=10;
        ms5=5;
        temp=0;

        n=0;
        _mfe=1; //开多功能中断
    _ctm0ae=1; //CTM a中断使能
        _emi=1;        //开总中断
        _ct0on=1; //开定时器
             com1=1;com2=1;com3=1;
                com4=1;
        }
        void main()
        {
                init();
                while(1)
                {
       
                        if(Flag_T1ms)
                        {
                        Flag_T1ms=0;
                        key_10ms++;
                        if(key_10ms==10)
                        {
                        key_10ms=0;
                        read_key();
                        }

                        }
                       
                        GCC_CLRWDT();
                }
        }
       
        void __attribute__((interrupt(0x14))) ISR_CTMO(void)
        {
                _ctm0af=0;
                s--;
                Flag_T1ms=1;
                if(! s)
                {   
                        s=1000;//1s电子钟计数
                        sec++;       
                if(sec==60)
                {
               sec=0;
               min++;
               if(min==60)
               {
                min=0;
                 hour++;
                if(hour==24)
                {
                  hour=0;
                }
               }
               }
                }
        }

       
       
       
       
回复

使用道具 举报

ID:358998 发表于 2018-7-6 17:42 | 显示全部楼层
已完成长短按。。。


#include "BS87D20A-3.h"
#define com1    _pc1
#define com2        _pc0
#define com3        _pc2
#define com4        _pc3
#define key1    _pd2
#define key2        _pd3
#define key3        _pa1
#define key4    _pa4
volatile bit Flag_T1ms;
volatile bit Flag_T5ms;
volatile bit flag_keylong;
volatile bit flag_keyshort;

const unsigned char tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};
unsigned char strtab[3];//缓冲区
unsigned char key_number=0;
unsigned char sec=0,min=0,hour=0;
unsigned char temp;
unsigned long s;  //秒级
unsigned long ms5;

unsigned char keyvalue;
void read_key()
{  
        static char key_state=0x00,press_20ms;
    unsigned char        keybak;       
    keybak=0;
        if(!key1)keybak|=0x01;
        if(!key2)keybak|=0x02;
        if(!key3)keybak|=0x04;
        if(!key4)keybak|=0x08;
   
    switch (key_state)
    {
        case 0x00:                 // 按键初始态
                if (keybak!=0)
                        {       
                                press_20ms=0;
                                key_state=0x01; // 键被按下,状态转换到键确认态
                               
                }
                        break;               
        case 0x01:                  // 按键确认态
            if (keybak!=0)
            {
                    if(++press_20ms>3)
                    {
                            key_state=0x02;
                            press_20ms=0;
                            keyvalue=keybak;               
                    }
            }
            else
            {
                    key_state=0x00;       
            }
            break;
                case 0x02:
                        if (keybak==0)
                        {
                                flag_keyshort=1;
                        }
                        else if(++press_20ms>100)
                        {
                                flag_keylong=1;
                        }       
        case 0x04:
            if(keybak==0)
            {
                    if(++press_20ms>3)
                    {
                            key_state=0x00;
                    }
            }
            else
            {
                    press_20ms=0;
            }
            break;
       
        default:
                break;
   }
}
void key_do()
{
        if(flag_keyshort)
        {
                switch(keyvalue)
                {
                        case 0x01:

                                break;
                        case 0x02:
                               
                                break;
                        case 0x04:
                               
                                break;
                        case 0x08:
                               
                                break;
                        default:
                                break;
                }
                flag_keyshort=0;
        }
}

void displaypro()
{
        strtab[0]=tab[sec%10];
        strtab[1]=tab[sec/10];
        strtab[2]=tab[min%10];
        strtab[3]=tab[min/10];

}
void display_drive()
{
        com1=1;com2=1;com3=1;com4=1;
                    switch(temp)
                {
                        case 0:com4=0;
                         _pb=strtab[temp]; break;
                        case 1:com3=0;
                         _pb=strtab[temp]; break;
                        case 2:com2=0;
                         _pb=strtab[temp]; break;
                        case 3:com1=0;
                         _pb=strtab[temp]; break;
                        default:break;
                }
                temp++;
                if(temp==4)
                        temp=0;

}
void init()
{
    _ctm0c0=0x20;  // fh/16   2us        
        _ctm0c1=0xc1; // 定时/计数器模式 比较器a ctm0
        _ctm0al=0xf4; // 1ms
    _ctm0ah=0x01;
       
        _ctm1c0=0x20;  // fh/16   2us        
        _ctm1c1=0xc1; // 定时/计数器模式 比较器a ctm1
        _ctm1al=0xf4; // 1ms
    _ctm1ah=0x01;
       
       
       
        _pbc=0; //输出
        _pcc0=0;
        _pcc1=0;
        _pcc2=0;
        _pcc3=0;
       
        _pac1=1;
        _pac4=1;
        _pdc2=1;
        _pdc3=1;
        _pdpu3=1;
        _pdpu2=1;
        _papu1=1;
        _papu4=1;

         s=1000;
         ms5=5;
         temp=0;
        _mfe=1; //开多功能中断
        _ctm1ae=1;
    _ctm0ae=1; //CTM a中断使能
        _emi=1;        //开总中断
        _ct0on=1; //开定时器0
        _ct1on=1;
        }
        void main()
        {
                init();
                while(1)
                {
                        if(Flag_T5ms)
                        {
                                Flag_T5ms=0;
                                read_key();
                                displaypro();
                               
                        }
       
                       
                        GCC_CLRWDT();
                }
        }
       
        void __attribute__((interrupt(0x20))) ISR_CTM1(void)
        {
                _ctm1af=0;
                ms5--;
                if(!ms5)
                {
                        ms5=5;
                        Flag_T5ms=1;
                }
                display_drive();
                s--;
                if(! s)
                {   
                       
                        s=1000;//1s电子钟计数
                        sec++;       
                        if(sec==60)
                        {
                               sec=0;
                               min++;
                               if(min==60)
                               {
                                        min=0;
                                         hour++;
                                        if(hour==24)
                                        {
                                                  hour=0;
                                        }               
                               }
                       }       
                }
               
        }
       
        void __attribute__((interrupt(0x14))) ISR_CTMO(void)
        {
                _ctm0af=0;
               
        }

       
       
       
       

评分

参与人数 1黑币 +80 收起 理由
admin + 80 回帖助人的奖励!

查看全部评分

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表