Encoder is passive or active electronic device that translates angular motion to analog or digital signals. Encoder shown on image below is passive incremental encoder with 2 outputs and pushbutton under its shaft. How do we use it in combination with arduino, or any other micro controller, will be explained in next chapter.
On image below we can see schematics of encoder.
Pins CLK and DT have pullup resistor (meaning they are active low) while SW has pull down resistor (meaning its active high). We will use this later to connect encoder to Arduino UNO.
Before we get into codding, we need to know how this encoder works in order to determine how to read its output. On image below you can see output signals from CLK and DT.
Image shown on left is when encoder is rotated counter clockwise (CCW) for one step, and on right when its rotated clockwise (CW) for one step. In case encoder is rotated CW, if we look at moment when CLK is rising, we can see that DT signal is at low level. For case if encoder is rotated CW, its vice versa, that is, while CLK is rising DT is at high level. We can use this to determine at which direction is encoder rotated by triggering micro controller on rising or falling CLK signal and reading DT state.
Alright, now when we know basics, we can get into programming an Arduino UNO micro controller to utilise encoder to turn on one of the leds that determines if encoder is rotated CW or CCW. Arduino UNO have 2 pins that can be setted up as external trigger input, that is, they can innitiate program functions from outside the micro controller. Pin 1 will be connected to CLK signal, pin 2 will be connected to SW and pin 3 will be connected to DT.
// encoder pins
#define ENCODER_CLK 2
#define ENCODER_DT 4
#define ENCODER_SW 3
// LED pins
#define LED_CW 5
#define LED_CCW 6
#define LED_SW 7
void setup()
{
pinMode(ENCODER_CLK, INPUT);
pinMode(ENCODER_DT, INPUT);
pinMode(ENCODER_SW, INPUT);
pinMode(LED_CW, OUTPUT);
pinMode(LED_CCW, OUTPUT);
pinMode(LED_SW, OUTPUT);
attachInterrupt(digitalPinToInterrupt(ENCODER_CLK), encoder_rotate_clk, RISING);
attachInterrupt(digitalPinToInterrupt(ENCODER_SW), encoder_sw_press, RISING);
}
void loop()
{
//does nothing here
}
void encoder_rotate_clk()
{
// turned CW
if (digitalRead(ENCODER_DT) == HIGH)
{
digitalWrite(LED_CW, HIGH);
digitalWrite(LED_CCW, LOW);
}
// turned CCW
else if(digitalRead(ENCODER_DT) == LOW)
{
digitalWrite(LED_CW, LOW);
digitalWrite(LED_CCW, HIGH);
}
}
void encoder_sw_press()
{
// toggle switch LED state
digitalWrite(LED_SW, !digitalRead(LED_SW));
}
If you have flickering while testing code above, don't worry, you havent broke anything. Encoder have one major problem and thats bouncing of contacts. This can be solved with adding capacitor in parallel with CLK, DT and SW pins on encoder, or by using software debounce, aka telling microcontroller to wait for some time before reading next state. Code below have software debounce implemented.
// encoder pins
#define ENCODER_CLK 2
#define ENCODER_DT 4
#define ENCODER_SW 3
// LED pins
#define LED_CW 5
#define LED_CCW 6
#define LED_SW 7
// debounce variable
bool debounce_start = false;
void setup()
{
pinMode(ENCODER_CLK, INPUT);
pinMode(ENCODER_DT, INPUT);
pinMode(ENCODER_SW, INPUT);
pinMode(LED_CW, OUTPUT);
pinMode(LED_CCW, OUTPUT);
pinMode(LED_SW, OUTPUT);
attachInterrupt(digitalPinToInterrupt(ENCODER_CLK), encoder_rotate_clk, RISING);
attachInterrupt(digitalPinToInterrupt(ENCODER_SW), encoder_sw_press, RISING);
}
void loop()
{
// resets debounce timer every 200ms;
if(debounce_start)
{
delay(200);
debounce_start = false;
}
}
void encoder_rotate_clk()
{
if(!debounce_start)
{
// turned CW
if (digitalRead(ENCODER_DT) == HIGH)
{
digitalWrite(LED_CW, HIGH);
digitalWrite(LED_CCW, LOW);
}
// turned CCW
else if(digitalRead(ENCODER_DT) == LOW)
{
digitalWrite(LED_CW, LOW);
digitalWrite(LED_CCW, HIGH);
}
debounce_start = true;
}
}
void encoder_sw_press()
{
if(!debounce_start)
{
// toggle switch LED state
digitalWrite(LED_SW, !digitalRead(LED_SW));
debounce_start = true;
}
}
Schematic used for connecting Arduino UNO, encoder and LEDs is shown below
I hope that you have learned how to use rotational encoder within Your projects and that You will create something awesome!
Some extra pics