手を振りかざすと白旗を上げて降参する Arduino
簡単な説明
赤外線の距離センサは、超音波距離センサと比較して測定できる距離は短めですが、残響を気にする必要がないため短時間に連続して値を取得できます。そのため、接近する物体との距離に応じたサーボモータの制御をリアルタイムに行うことができたりします。
作り方 1ページ目 (全 1 ページ)

必要なパーツ

セロハンテープ、つまようじ、ティッシュペーパーは、サーボモータに持たせる白旗を作るためのものです。

回路図

GP2Y0A21YK は瞬間的に大きな電流が必要になることがあるため、電解コンデンサを付近に設置しています。出力電圧を A0 ピンで A/D 変換して読み取ります。Servo モーターはパルス幅によってその角度を指定します。Servo ライブラリを利用すれば Arduino の PWM ピンから簡単に制御できます。

Uploaded Image

http://schematics.com/project/white-flag-waver-48553/

制御プログラム

サーボモータの不要な振動を抑制するために、過去の距離センサの値を記憶して平均したり、一の位と十の位の値を切り捨てたりしています。servo.write() には 0-180 の値を入力できますが、距離センサが 3V 程度の電圧までしか出力しないため、実際に白旗が振り上がるのは 108 度程度までとなります。

#include <Servo.h>

#define SERVO_PWM_PIN 13
#define DISTANCE_INPUT_PIN 0

// サーボモータを制御するためのオブジェクトを生成
Servo servo;

// サーボモータをできるだけなめらかに制御するために、
// 過去の距離センサの値を記憶します。
const int BUF_SIZE = 64;
int buf[BUF_SIZE];
int k = 0;

void setup() {
  // サーボモータの初期化
  servo.attach(SERVO_PWM_PIN);

  // 距離センサの値で配列を初期化
  for(int i = 0; i < BUF_SIZE; ++i) {
    buf[i] = analogRead(DISTANCE_INPUT_PIN);
  }
}

void loop() {

  // 距離センサから値を読み取ります。
  buf[k] = analogRead(DISTANCE_INPUT_PIN);

  // 過去の距離センサの値を平均します。
  long avg = 0;
  for(int i = 0; i < BUF_SIZE; ++i) {
    avg += buf[i];
  }
  avg /= BUF_SIZE;

  // サーボモータの角度を計算して PWM 制御します。
  // 一の位と十の位を切り捨てることで、サーボモータの不要な振動を抑制します。
  int deg = map(avg/100, 0, 10, 0, 180); // 0-1023 を 0-180 に変換
  servo.write(deg);

  // 次のインデックスに進めます。
  k = (k + 1) % BUF_SIZE;
}