原创 旋转编码器

2009-11-10 19:59 2860 19 20 分类: MCU/ 嵌入式


    很好的旋转编码器的读码程序,设旋转编码器的输出波形如下
                 ______        ______        ______        ______
正转时:  A相   __|      |______|      |______|      |______|   
                      ______        ______        ______        ___
         B相   ______|      |______|      |______|      |______|  
低位为A相         01  11 10  00 01  11 10  00 01  11 10  00 01  11
                     ______        ______        ______        ______
反转时:  A相   ______|      |______|      |______|      |______|   
                  ______        ______        ______        ___
         B相   __|      |______|      |______|      |______|  
低位为A相         10 11  01  00 10  11 01  00 10  11 01  00 10  11
A相接在某端口上,对应检测代码为 if((REG32(P4SIN) & (1<<3)))  PhaseShift |= 0x01;
B相接在某端口上,对应检测代码为 if((REG32(P1SIN) & (1<<2)))  PhaseShift |= 0x02;
PhaseShift的<1:0>两位表示当前AB两相的状态,<3:2>两位表示上一次AB两相的状态
正转时,AB相变化顺序为   01->11->10->00->01    低位为A相
因此正转时,PhaseShift的低四位值为 0111 1110 1000 0001
反转时,AB相变化顺序为   10->11->01->00->10    低位为A相
因此反转时,PhaseShift的低四位值为 1011 1101 0100 0010
*/
/* 假设正转为减,反转为加,则可得如下一表 */
const u8 table_Phase[16]=
{
  phase_no_move,    // 0000 未转动
  phase_dec,        // 0001 正转
  phase_inc,        // 0010 反转
  phase_bad,        // 0011 不可能
  phase_inc,        // 0100 反转
  phase_no_move,    // 0101 未转动
  phase_bad,        // 0110 不可能
  phase_dec,        // 0111 正转
  phase_dec,        // 1000 正转
  phase_bad,        // 1001 不可能
  phase_no_move,    // 1010 未转动
  phase_inc,        // 1011 反转
  phase_bad,        // 1100 不可能
  phase_inc,        // 1101 反转
  phase_dec,        // 1110 正转
  phase_no_move,    // 1111 未转动
};
/* 根据PhaseShift的低四位值来查此表即可得转动方向 */
PhaseShift &= 0x0f;
if(table_Phase[PhaseShift] == phase_inc) PhaseCount++;
if(table_Phase[PhaseShift] == phase_dec) PhaseCount--;
/* 当同一方向上的转动次数为4次时,才认为是一次有效的转动,达到了去抖的目的 */
if(PhaseCount > 3)
{
  PhaseCount -= 4;
   return phase_inc;
}
else if(PhaseCount < -3)
{
  PhaseCount += 4;
   return phase_dec;
}

文章评论1条评论)

登录后参与讨论

southcreek 2009-11-10 21:48

实在没有必要弄这么麻烦。 将编码器的一个输出接到一根中断线上,另一根接到I/O线上。当产生中断时,马上读另一根线的状态。如果为高就是正转,反之则这反转。电路设计中注上上拉和加上电容滤抖动就行了。
相关推荐阅读
用户925035 2009-11-15 00:44
通用按键消抖函数 -- 数据与过程分离
AUTO:  nicksean 不务正业          项目里经常处理按键消抖, 本来这个消抖的过程是与具体按下的键无关的, 可以前的代码总是在消抖的同时处理具体的按键值, 再加上长按 短按 组合...
用户925035 2009-11-13 13:16
液晶ST7920串行显示
液晶显示128*64以7920为主控制器,采用3线制,比较经济简单。代码如下.....
用户925035 2009-11-13 13:11
DS18B20 C51完整版
使用WINBOND W78C516单片机,11.0592MHZ晶振,用共阳LED数码管P0口输出段码,P1口扫描/*******************************************...
用户925035 2009-11-12 13:19
74HC164驱动数码管
          74HC164是串行输入,并行输出接口器件,可用在单向的并行输出/并行地址锁存等. 74HC164因为价格便宜,容易使用特别适合使用在在需要用到数码管显示IO口又比较紧张的电子产品...
用户925035 2009-11-10 20:13
at24c512多字节读写函数 欢迎测试
刚写的at24c512多字节读写函数,欢迎测试。/********************************************************************函数功能:EE...
我要评论
1
19
关闭 站长推荐上一条 /2 下一条