AI要約
Amazonで購入した自動車用バックセンサーを活用し、Arduinoで障害物との距離を測るシステムを試作。実験の様子も含め、制作過程を解説しています。
やること
ロボットの衝突防止のために近接センサーを導入するぞ、の第③弾です。だんだん飽きてきました。
自動車用のバックセンサーというものがあります。バックするときに「ピッピ・・・」「ピーーー」と鳴るやつですね。Amazonで中華コピー品が2000円台から買えます。センサーとしては超音波式で、4~8個を統合してレベルゲージやブザーで運転席に知らせてくれます。
この信号を取り出せたら楽じゃないか、ということで車のバックセンサーから検出距離を取り出せないか検証してみます。
材料
Amazonで「バックセンサー」で出てきた2000円の商品を買いました。たぶんこの価格帯のはみんな同じ基板だと思います。

動作確認しようと思ったらまさかのセンサーの端子が4個挿さらない!ギチギチじゃないか (#^ω^)ピキピキ

製品としての動作は以下動画の序盤「1. バックセンサーの挙動」をご覧ください。超音波式はやはりガバガバですね・・・
どこから信号を取り出すか?
どこから信号を取り出そうかなとあちこちにテスターを当ててみると、ブザー信号に直流12Vが出ているみたいです。ブザーはこの製品には付属しておらず、端子が空いています。LEDを繋いでみると検出距離に応じて4段階で点滅速度が変わりました。1.6m以下で「ピッピ…」と点滅し始め、0.4m以下で「ピー」になります。
動画の中盤「2. バックセンサーのブザー信号が取り出せそう」をご覧ください。ブザー信号(LED)とモニターのブザー音(鳴っている音)は微妙にしきい値が違うようです。揃えたらいいのに・・・
他に、モニター(レベルゲージ)の端子からもっと細かい階調で取れそうですが、面倒くさそうなので今回はやめときます。
ブザー信号の12Vを10kΩと5kΩで分圧して4V(>2.7V HIGH)をArduinoのD2ピンに入れました。

コード
D2ピンを検出して、直近1秒間のHIGHの比率に応じて接近レベル0~3の4段階で判定しました。バックセンサーのブザー信号と同じ4段階になるようにしきい値を調整しました。
//バックソナーからの入力ピン
const int sonarPin = 2;
//Arduinoのブザーピン
const int buzzerPin = 11;
const int WINDOW_SAMPLES = 20; //1秒のウインドウ (50ms × 20回)
bool windowBuf[WINDOW_SAMPLES];
int indexPos = 0;
int highCount = 0;
void setup() {
Serial.begin(9600);
//センサー初期化
pinMode(sonarPin, INPUT);
//ブザー初期化
pinMode(buzzerPin, OUTPUT);
digitalWrite(buzzerPin, LOW);
//バッファ初期化(すべてLOWとして扱う)
for (int i = 0; i < WINDOW_SAMPLES; i++) {
windowBuf[i] = false;
}
}
void loop() {
//バックソナーの信号読み取り
bool sonarHigh = digitalRead(sonarPin);
//Arduinoのブザーを鳴らす
if (sonarHigh) {
tone(buzzerPin, 442); //4kHz
} else {
noTone(buzzerPin); // ブザー OFF
}
//移動ウインドウに現在の値を入れると同時に古い値を引く
if (sonarHigh && !windowBuf[indexPos]) {
highCount++; // LOW→HIGH に変わった
} else if (!sonarHigh && windowBuf[indexPos]) {
highCount--; // HIGH→LOW に変わった
}
windowBuf[indexPos] = sonarHigh;
indexPos = (indexPos + 1) % WINDOW_SAMPLES;
//HIGH率
float highRatio = (float)highCount / (float)WINDOW_SAMPLES;
Serial.print("High ratio: ");
Serial.print(highRatio, 2);
Serial.print(" -> ");
//判定
if (highRatio <= 0.10) {
Serial.println("Level 0");
} else if (highRatio <= 0.35) {
Serial.println("Level 1");
} else if (highRatio <= 0.80) {
Serial.println("Level 2");
} else {
Serial.println("Level 3");
}
//ループ待機[ms]
delay(50);
}結果
動画の終盤「3. バックセンサーのブザー信号が取り出せた」のとおりです。
直近1秒間の情報を使うので少し時間遅れが生じてしまいます。それ以前に超音波式の安定性はダメですね。。これ車に付けてちゃんと動作するのだろうか…?
おわりに
もう一つ自動車用の近接センサーを買ったので次回試してみます。
