ロータリーエンコーダー (機械接点式インクリメンタル型) の信号をデコードするクラスです。 Rotary Encoder (incremental, mechanical switch type) signal decoder class.
Revision 0:fcf360069f17, committed 2014-09-07
- Comitter:
- tetsuya256
- Date:
- Sun Sep 07 23:31:47 2014 +0000
- Commit message:
- First commit.
Changed in this revision
RotaryEncoder.cpp | Show annotated file Show diff for this revision Revisions of this file |
RotaryEncoder.h | Show annotated file Show diff for this revision Revisions of this file |
diff -r 000000000000 -r fcf360069f17 RotaryEncoder.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/RotaryEncoder.cpp Sun Sep 07 23:31:47 2014 +0000 @@ -0,0 +1,26 @@ +#include <RotaryEncoder.h> + +RotaryEncoder::RotaryEncoder(PinName A, PinName B) + : terminalA(A, PullUp), terminalB(B, PullUp) +{ +} + +void RotaryEncoder::attach(void (*callback)(int)) { + callbackFunc = callback; + tick.attach_us(this, &RotaryEncoder::smpling, RotaryEncoder_SamplingInterval); +} + +void RotaryEncoder::detach() { + tick.detach(); +} + +void RotaryEncoder::smpling() { + static uint8_t val = 0xFF; + uint8_t now = (terminalA.read() << 1) | (terminalB.read()); + if (now == (val & 0x03)) return; + val = (val << 2) | now; + switch (val) { + case 0x4B: (*callbackFunc)(1); break; // cw : 0b01001011 = 0x4B + case 0x87: (*callbackFunc)(0); break; // ccw : 0b10000111 = 0x87 + } +}
diff -r 000000000000 -r fcf360069f17 RotaryEncoder.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/RotaryEncoder.h Sun Sep 07 23:31:47 2014 +0000 @@ -0,0 +1,112 @@ +#ifndef RotaryEncoder_H +#define RotaryEncoder_H + +#include <mbed.h> + +#define RotaryEncoder_SamplingInterval 2000 // Sampling interval (us) + +/** + * ロータリーエンコーダー (機械接点式インクリメンタル型) の信号をデコードするクラスです。<br /> + * Rotary Encoder (incremental, mechanical switch type) signal decoder class.<br /> + * Copyright(C)2014 T.Hoshino<br /> + * <br /> + * CAUTION: My English is very poor, it might be wrong. (I rely on Google Translate almost.) + * <ul> + * <li>コンストラクタに指定した2つのピンは「入力・内蔵プルアップ有効」に設定されます。外部プルアップは必要ありません。<br /> + * Two pins that you specified in constructor parameter is set to "input, built-in pull-up enabled". There is no need for external pull-up. + * </li> + * <li>機械接点のチャタリングは、Ticker による2ミリ秒ごとのサンプリングで回避します。RCローパスフィルタは必要ありません。<br /> + * This will debounced by software signal sampling. RC lowpass filter is not required. + * </li> + * <li>回転検出時は #attach で指定したコールバック関数を呼び出します。<br /> + * Will invoke the callback function you specified in #attach method when detected rotation. + * </li> + * <li>回転方向はコールバック関数のパラメータで判別できます。右回りなら 1、左回りなら 0 です。<br /> + * Can detect rotate direction in the parameter of callback function. If clockwise, It's 1. If counterclockwise, It's 0. + * </li> + * <li>以下のようなデバイスでの正常動作を確認しています。<br /> + * It has been confirmed the correct operation of following devices.<br /> + * http://akizukidenshi.com/catalog/g/gP-05651/ + * </ul> + * @code +//---------------------------------------- +// Sample code for ST Nucleo F401RE +//---------------------------------------- +#include <mbed.h> +#include <AQM0802A.h> +#include <RotaryEncoder.h> + +AQM0802A lcd(D14, D15); // I2C Character LCD +RotaryEncoder rotary(D8, D9); // <-- this! + +// RotaryEncoder callback function +// cw = 1:clockwise, 0:counterclockwise +void rotate(int cw) { + static int value = 0; + value += cw ? 1 : -1; + lcd.cls(); + lcd.printf("%d", value); +} + +int main() { + lcd.printf("Rotary\n Encoder"); + rotary.attach(&rotate); + while(1) { + sleep(); // sleep() is optional + } +} + * @endcode + * ご自由にお使いいただけますが、無保証です。使用は自己責任でどうぞ。<br /> + * The use of this is free, but no warranty. please use at your own risk.<br /> + */ +class RotaryEncoder { + public: + + /** + * コンストラクタです。<br /> + * Constructor.<br /> + * ロータリーエンコーダーの信号線に接続されたピンを指定してください。<br /> + * Specify pins connected to the signal line of rotary encoder.<br /> + * どちらのピンも「入力、内蔵プルアップ有効」に設定されます。<br /> + * Both pins are set to "input, built-in pull-up enabled". + * @param A Terminal A signal input pin. + * @param B Terminal B signal input pin. + */ + RotaryEncoder(PinName A, PinName B); + + /** + * ロータリーエンコーダーの回転検出時に呼び出すコールバック関数を登録します。<br /> + * Register callback function to be called, when detect rotary encoder rotate.<br /> + * <ul> + * <li>ロータリーエンコーダーの信号サンプリングもここから開始されます。<br /> + * Signal sampling of rotary encoder also starts from here. + * </li> + * <li>回転検出時は、回転方向がt時計回りならパラメータに 1 を、反時計回りなら 0 を渡してコールバック関数を呼び出します。<br /> + * When detect rotation, Call the callback function with int parameter. If clockwise, parameter is 1. Otherwise(counterclockwise) 0.<br /> + * コールバック関数の定義方法は、クラス概要のサンプルコードを参照してください。<br /> + * How to define callback function, please refer to the sample code for class description. + * </li> + * </ul> + * @param callback 登録するコールバック関数。 Callback function to be registered. + * @see #detach() + */ + void attach(void (*callback)(int)); + + /** + * #attach で登録したコールバック関数を切り離します。<br /> + * Detach the callback function that was registered in #attach method.<br /> + * ロータリーエンコーダーの信号サンプリングも停止します。<br /> + * Also stop signal sampling of rotary encoder. + * @see #attach + */ + void detach(); + + private: + DigitalIn terminalA; + DigitalIn terminalB; + Ticker tick; + void smpling(); + void (*callbackFunc)(int); +}; + +#endif