[Atmel] 用AVR单片机的ADC功能实现1个I/O口连接4个按键

[复制链接]
1005|5
 楼主| 奥德赛 发表于 2015-8-31 21:33 | 显示全部楼层 |阅读模式
最近用AVR的M48作一个东西,这一个口那一个口突然发现IO口不够用了。用扩展芯片是没问题,但是感觉太浪费了,恰巧AVR有ADC功能,我看到好多人用ADC功能做按键一个IO口实现24按键,我就4个按键做起来应该不是很难。看完datasheet的ADC和参考网上资料,程序写完以后运行效果还不错,下面是电路图和源程序:
  1.     /*
  2.     *************************************************************************
  3.     *名称: unsigned int GetADCValue(unsigned char uchADCChannel)     *
  4.     *功能: 获取按键ADC值             *
  5.     *参数: 无                                   *
  6.     *返回: 按键ADC值                                 *
  7.     *************************************************************************
  8.     */   
  9.     unsigned int GetADCValue(unsigned char uchADCChannel)
  10.       {
  11.        unsigned char i;
  12.        unsigned int uiADCValue = 0;
  13.       
  14.        ADMUX = _BV(REFS0)|uchADCChannel;          // 参考电压AVCC选择
  15.        for (i=0; i<4; i++)                 // 连续转换4次
  16.         {
  17.          ADCSRA |= (1<     ADCSRA |= (1<     loop_until_bit_is_set(ADCSRA, ADIF); // 等待ADC转换结束
  18.          ADCSRA |= (1 << ADIF);      // 写1清除标志位
  19.          uiADCValue =uiADCValue + ADC;     
  20.          
  21.         }
  22.       
  23.        uiADCValue /= 4;        // 取平均值
  24.        return uiADCValue;
  25.       }
  26.     /*
  27.     *************************************************************************
  28.     *名称: unsigned char GetKeyValue(void)          *
  29.     *功能: 获取按键值              *
  30.     *参数: 无                                   *
  31.     *返回: 按键值                                  *
  32.     *************************************************************************  
  33.     */
  34.     unsigned char GetKeyValue(void)
  35.     {
  36.       // 5.24V下按键与对应ADC值如下
  37.       // KEY  NO  KEY0     KEY1  KEY2  KEY3
  38.       // ADC  1023 0012 390     565  669

  39.       unsigned char uchKeyValue = NOKEY;  // 按键码
  40.       unsigned int uiKeyADC = 0;    // 按键ADC值
  41.       uiKeyADC = GetADCValue(ADC_CHANNEL);
  42.       if(uiKeyADC<1000)      // 如果有键按下  
  43.        {
  44.         DelayNms(10);     // 延时10ms消抖   
  45.         uiKeyADC = GetADCValue(ADC_CHANNEL);
  46.         if(uiKeyADC < 32)     // KEY0
  47.          {
  48.           uchKeyValue = KEY0;
  49.          }
  50.         else if(uiKeyADC < 410)    // KEY1
  51.          {
  52.           uchKeyValue = KEY1;
  53.          }
  54.         else if(uiKeyADC < 585)    // KEY2
  55.          {
  56.           uchKeyValue = KEY2;
  57.          }
  58.         else if(uiKeyADC < 689)    // KEY3
  59.          {
  60.           uchKeyValue = KEY3;
  61.          }
  62.        }
  63.       return uchKeyValue;  
  64.     }


波越 发表于 2015-8-31 21:43 来自手机 | 显示全部楼层
r是什么原理?
波越 发表于 2015-8-31 21:44 来自手机 | 显示全部楼层
上拉电阻的不同吗
会飞の鱼 发表于 2015-8-31 21:52 | 显示全部楼层
楼主做4个按键还是挺幸运的,代码量也不是很多。
xyz549040622 发表于 2015-8-31 22:11 | 显示全部楼层
楼主图片挂了,应该是电阻分压,然后不同的按键按下的时候,有不同的电压值。但这么做也有缺点,反应比较慢。
lzbf 发表于 2015-8-31 22:16 | 显示全部楼层
键盘扫描么?
您需要登录后才可以回帖 登录 | 注册

本版积分规则

46

主题

397

帖子

3

粉丝
快速回复 在线客服 返回列表 返回顶部