と、言っては見たものの実際にArduinoを使ってどんな物を作るのかと聞かれると、具体的なアイデアは直ぐには出てきません。
そんなこんなで、動作確認くらいしかできていなかったArduinoですが、とある行事に参加することになりまして、そこで簡単なアンケートみたいなものをすることになりました。
アンケートと言っても用紙に何かを記入してもらうようなものではなく、単純な二捨択一式(好きとか嫌いとか)で気軽に済ませられるもので、ボタンを二つ用意してその数を集計するだけのもので十分に物足ります。
アナログ的に考えれば、電子カウンタとボタンを繋ぐだけで済ませてしまいたい感じですが、せっかくArduinoがあるので、PCと通信させて視覚的にも凝ったカウンタにできれば理想的です。
- ボタンの入力をArduinoで検知してシリアルポートに情報を送信
- PC上のサーバーでTCPポートを監視し、シリアルポートの情報をTCPポートへ転送
- Flashアプリを作成、TCPポートを監視して、入力があれば情報を受信しカウンタを更新
2番目の処理は、シリアルポートへ直接アクセスできないFlashアプリとArduinoを通信させるためのもので、一番厄介そうな部分ですが、とりあえずは必要ありません。
用意したものは、
- Arduino Duemilanove
- プッシュボタン2個(何でもOK)
- 1kΩ抵抗2個(プルダウン用)
- Arduino IDE
さて、問題なくArduino IDEが動いたら、早速プッシュボタンを図のようにプルダウン抵抗を入れて接続します。
下記のようにスケッチを書いてコンパイル、Arduinoへアップロードします。
int btPin = 2;
int ledPin=13;
int pinState = LOW;
void setup() {
pinMode(btPin, INPUT);
pinMode(ledPin, OUTPUT);
}
void loop() {
pinState = digitalRead(btPin);
if (pinState == HIGH) {
digitalWrite(ledPin, HIGH);
} else {
digitalWrite(ledPin, LOW);
}
}
ボタンを押した時に基板上のLEDが点灯すれば、ひとまずはOKです。次に、シリアル経由でボタンが押されたら、ボタンが押されたと言う信号を送信するように変更してみましょう。
int btPin = 2;
int pinState = LOW;
void setup() {
pinMode(btPin, INPUT);
Serial.begin(9600);
}
void loop() {
pinState = digitalRead(btPin);
if (pinState == HIGH) {
Serial.println("Pushed!");
}
}
シリアル経由で信号が送信されているかどうかは、Arduino IDEのシリアルモニター機能を使います。
シリアルモニターをONにしてボタンを押すと・・・確かに”Pushed!"と表示されてはいますが、ボタンを一回押しただけなのに何回も”Pushed!"が送信されています。
これではボタンが押されたかどうかの判定ができず使い物になりません。
電子カウンタなら電圧の入力時間そのものが比較的長く緩慢なため、ボタンを押すくらいの時間なら一回押されたと判定する(感度の調整によります)のですが、Arduinoには通用しません。
デジタルなArduinoは、マイコンがプログラムを実行するサイクル時間でボタンが押されているかどうかを判定してしまうため、例えボタンを幾ら早押ししてもマイコンからすれば軽く数十サイクルが過ぎてしまうためです。
これはバウンスと呼ばれ、機械的に回避することができないのでソフト側で対応する必要があります。
たかだかボタン(スイッチ)なのに厄介なものです。
バウンスを回避するには、一定の時間内は同じ判定結果を出さなければ良い、すなわちボタンが押された瞬間に”ON”であれば、一定時間の間にまた”ON”と言う判定が出た場合は無視すると言うプログラムを書けばよいことになります。
この一定時間と言うのは、ボタンの構造等によって左右されますが、何回か試せば最適な時間が導き出せると思います(ここでは20ms)。
何となくアルゴリズムは理解できましたが、実はArduinoの公式サイトには豊富なライブラリがすでに用意されていて、その中にボタン入力の際のバウンスを回避する”デバウンス”と言うライブラリが存在します。
ライブラリを指定通り”/hardware/libraries”にコピーし、
#includeこんな感じにスケッチを変更します。#define BtPin 2 // 20msをデバウンス用に定義 Debounce debouncer = Debounce(20, BtPin); void setup() { pinMode(BtPin, INPUT); Serial.begin(9600); } void loop() { if (debouncer.update() && debouncer.read() == HIGH) { Serial.println("Pushed!"); } }
コンパイルに問題がなければArduinoにアップロードしてシリアルモニターを実行してみます。
ボタンを一回押すと、”Pushed!”が一回だけ、モニター画面に表示されるはずです。
| < 戻る | 次 > |
|---|



