diff --git a/src/rotary.cpp.txt b/src/rotary.cpp.txt new file mode 100644 index 0000000..d626e21 --- /dev/null +++ b/src/rotary.cpp.txt @@ -0,0 +1,90 @@ + /* interrupt routine for Rotary Encoders + tested with Noble RE0124PVB 17.7FINB-24 http://www.nobleusa.com/pdf/xre.pdf - available at pollin.de + and a few others, seems pretty universal + + The average rotary encoder has three pins, seen from front: A C B + Clockwise rotation A(on)->B(on)->A(off)->B(off) + CounterCW rotation B(on)->A(on)->B(off)->A(off) + + and may be a push switch with another two pins, pulled low at pin 8 in this case + raf@synapps.de 20120107 + +*/ + +// usually the rotary encoders three pins have the ground pin in the middle +enum PinAssignments { + encoderPinA = 2, // right + encoderPinB = 3, // left + clearButton = 8 // another two pins +}; + +volatile unsigned int encoderPos = 0; // a counter for the dial +unsigned int lastReportedPos = 1; // change management +static boolean rotating = false; // debounce management + +// interrupt service routine vars +boolean A_set = false; +boolean B_set = false; + + +void setup() { + pinMode(encoderPinA, INPUT); + pinMode(encoderPinB, INPUT); + pinMode(clearButton, INPUT); + // turn on pullup resistors + digitalWrite(encoderPinA, HIGH); + digitalWrite(encoderPinB, HIGH); + digitalWrite(clearButton, HIGH); + + // encoder pin on interrupt 0 (pin 2) + attachInterrupt(0, doEncoderA, CHANGE); + // encoder pin on interrupt 1 (pin 3) + attachInterrupt(1, doEncoderB, CHANGE); + + Serial.begin(9600); // output +} + +// main loop, work is done by interrupt service routines, this one only prints stuff +void loop() { + rotating = true; // reset the debouncer + + if (lastReportedPos != encoderPos) { + Serial.print("Index:"); + Serial.println(encoderPos, DEC); + lastReportedPos = encoderPos; + } + if (digitalRead(clearButton) == LOW ) { + encoderPos = 0; + } +} + +// Interrupt on A changing state +void doEncoderA() { + // debounce + if ( rotating ) delay (1); // wait a little until the bouncing is done + + // Test transition, did things really change? + if ( digitalRead(encoderPinA) != A_set ) { // debounce once more + A_set = !A_set; + + // adjust counter + if A leads B + if ( A_set && !B_set ) + encoderPos += 1; + + rotating = false; // no more debouncing until loop() hits again + } +} + +// Interrupt on B changing state, same as A above +void doEncoderB() { + if ( rotating ) delay (1); + if ( digitalRead(encoderPinB) != B_set ) { + B_set = !B_set; + // adjust counter - 1 if B leads A + if ( B_set && !A_set ) + encoderPos -= 1; + + rotating = false; + } +} +