Library for decoding quadrature encoders. Uses a ring buffer so you can be sure to process every tick in the order that it happened. This library is not really intended for public use yet and does not have much documentation.

Dependents:   LineFollowing DeadReckoning

Revision:
1:138f5421c287
Parent:
0:82ccff71d12a
Child:
2:22ac2b4a8012
--- a/PololuEncoder.h	Thu Feb 20 02:11:00 2014 +0000
+++ b/PololuEncoder.h	Thu Feb 20 18:54:43 2014 +0000
@@ -1,8 +1,8 @@
 #include <mbed.h>
 
-#define POLOLU_ENCODER_EVENT_INC  0b01000000
-#define POLOLU_ENCODER_EVENT_DEC  0b10000000
-#define POLOLU_ENCODER_EVENT_ERR  0b11000000
+#define POLOLU_ENCODER_EVENT_INC  0x40
+#define POLOLU_ENCODER_EVENT_DEC  0x80
+#define POLOLU_ENCODER_EVENT_ERR  0xC0
 
 #define POLOLU_ENCODER_BUFFER_SIZE 256
 
@@ -42,17 +42,9 @@
 
 class PololuEncoder
 {
-    private:
-    InterruptIn pinA;
-    InterruptIn pinB;
-    PololuEncoderBuffer * buffer;
-    uint8_t id;
-    
     public:
     PololuEncoder(PinName pinNameA, PinName pinNameB, PololuEncoderBuffer * buffer, uint8_t id)
       : pinA(pinNameA), pinB(pinNameB), buffer(buffer), id(id)
-//    PololuEncoder(PinName pinNameA, PinName pinNameB, uint8_t id)
-//      : pinA(pinNameA), pinB(pinNameB), id(id)
     {
         pinA.mode(PullUp);        // TODO: move this to the user code
         pinB.mode(PullUp);        // TODO: move this to the user code
@@ -61,13 +53,60 @@
         pinA.fall(this, &PololuEncoder::isr);
         pinB.rise(this, &PololuEncoder::isr);
         pinB.fall(this, &PololuEncoder::isr);
+        
+        previousState = readState();
     }
     
     void isr()
     {
-        if (buffer->hasSpace())
+        uint8_t event = 0;
+        uint8_t newState = readState();
+        switch((previousState << 2) | newState)
         {
-            buffer->writeEvent(0x23);
+        case 0x1: // 0b0001
+        case 0x7: // 0b0111
+        case 0xE: // 0b1110
+        case 0x8: // 0b1000
+            event = id | POLOLU_ENCODER_EVENT_INC;
+            count += 1;
+            break;
+        case 0x2: // 0b0010
+        case 0xB: // 0b1011
+        case 0xD: // 0b1101
+        case 0x4: // 0b0100
+            event = id | POLOLU_ENCODER_EVENT_DEC;
+            count -= 1;
+            break;
+        case 0x3: // 0b0011
+        case 0x6: // 0b0110
+        case 0x9: // 0b1001
+        case 0xC: // 0b1100
+            event = id | POLOLU_ENCODER_EVENT_ERR;
+            break;
+        }        
+        previousState = newState;
+        
+        if (event != 0 && buffer->hasSpace())
+        {
+            buffer->writeEvent(event);
         }
     }
+    
+    int32_t getCount()
+    {
+        return count;
+    }
+    
+    private:
+    uint8_t readState()
+    {
+        return pinA | (pinB << 1);
+    }
+    
+    InterruptIn pinA;
+    InterruptIn pinB;
+    PololuEncoderBuffer * buffer;
+    uint8_t previousState;
+    volatile uint8_t id;
+    volatile int32_t count;
 };
\ No newline at end of file