イノッチの鉄道模型ブログ

日常生活の中のトピックスを気ままに書きます。鉄道模型製作や畑作業が中心です。
これまで製作した鉄道模型作品は、ホームページ「イノッチの鉄道模型」inoyoshio.jimdo.comに載せていますので、こちらもよかったらみてください。

Arduinoで電車が動いた!

タイトルにあるように、マイコンで電車を動かせるなんて、この年でできるのか?
このギモンが解消されたときは、とにかくうれしかったです。その経緯を説明します。


① まずは準備部品から
Aruduino UNO(アルディーノ・ウノ)‥‥電子工作に便利なマイコン。安価でびっくり
ブレッドボード‥‥ハンダ付けせずに電子回路が組めるボードで、穴が多数あいている。
         入手したとき、こんな便利グッズがあるのかと感心しました。
TA7291P‥‥車両駆動用ドライバIC(ブレッドボードの中ほどにある。全10ピン)
      5番ピン、6番ピンのHIGH / LOW組み合わせで正走、逆走、停止を設定。
ボリウム‥‥速度調整用(ブレッドボード上の青い四角い部品)


テスト用線路とホーム‥‥この線路上を往復させます。ホームの横にはリードスイッチ
            (下の写真)を取り付けています。


リードスイッチ‥‥車両を停止させる位置を検出する磁気スイッチ。本体は20mm長。


永久磁石‥‥車両の横に10✕7mmの永久磁石を接着し、車両がホームに接近すると、ホームの横に付けたリードスイッチがONしてArduinoに伝えるしくみです。


②スケッチ(Arduinoで電車を動かすプログラム)の検討
往復運転をするためには、実用書の「TA7291PでDCモータを回す」、「LEDを繰り返し点滅させる」、「外部割込み関数を使う」あたりの内容を参考にスケッチを作りました。


ほぼ想定通り電車が動いてくれた時は感激しました。ただし、リードスイッチで検出したあと、停止時間なく すぐに逆走してしまいます。スケッチの内容的にはそれで正解なのですが、停止時間を5~10秒くらいは設けたい。そこで遅延関数(delay)を使えば いくらでも停止時間を設定はできるのですが、ここで問題発生。


リードスイッチ検出を利用した外部割込み関数(attachInterrupt)には遅延関数(delay)が併用できない、と本に書いてありました。案の定、エラー発生、万事休すです!


外部割込み関数(attachInterrupt)を使わないスケッチにしなければと思い、結局イフ関数(if)で構成することにしました。この「i f 文」の中では 遅延関数(delay)はいくらでも使えます。結果、うまく動きました。


もう一つの課題は、「急にガクンと停止。急にガクンと発進」という現状を、「自動的に 徐々に速度を落とす(または上げる)」、という制御ができないものか?という点です。


どうもこの頭ではムリみたいです。とりあえず 「 階段制御」にしました。停止の前に2段階の減速期間を設け、また 発進後1段階の助走期間を設けました。


ここまでで、ようやく動きがサマになりました。第1ステップクリアです。ジオラマ製作の合い間に、参考書を買ってから非常にゆっくりしたペースでトライしてきて ここまで来ました。以下に、第1ステップの内容を説明します。


③第1ステップクリア時点の配線全景

Arduinoとの接続関係写真です。
・パソコンへの通信ケーブルがArduinoからでています。
・ブレッドボードの左端には車両モータ駆動用のDC12vが入っています。
・線路へのフィーダーは上端にあります。
・2つのホームの中ほどに、それぞれリードスイッチRSa、RSbが接着されています。


④回路図

⑤自動往復運転の様子

Arduino自動往復運転(第1ステップ)
動画作業は初めてです。カメラを固定せずに撮ったので画面のフレはご容赦ください。
本来、手持ちの「Bトレの江ノ電」で考えていたのですが、速度ムラが多く、安定走行のDE10(貨物けん引用ディーゼル)で試行しています。


⑥最後にスケッチを載せます。
<自動往復運転 第1ステップ>
(ホームに来たら1秒づつ2段階の減速後停止。5秒後、助走発進し5秒後設定速度へ)
void setup(){
pinMode(2,INPUT);
pinMode(3,INPUT);
pinMode(9,OUTPUT);
pinMode(10,OUTPUT);
pinMode(11,OUTPUT);
digitalWrite(10,HIGH);  //正走
digitalWrite(11,LOW);
}
void loop(){
int val;
val=analogRead(0); //速度
analogWrite(9,val/4); //設定速度

if(digitalRead(3)==HIGH){ //RSb検出
analogWrite(9,val/6); //減速1秒間
delay(1000);
analogWrite(9,val/8); //更に減速1秒間
delay(1000);
digitalWrite(10,LOW); //停止5秒間
delay(5000);
digitalWrite(11,HIGH); //低速発車5秒間
analogWrite(9,val/6);         
delay(5000); // 低速発車後、確実にloopに戻して設定速度に移行させるための5秒
}
if(digitalRead(2)==HIGH){ //RSa検出
analogWrite(9,val/6); //減速1秒間
delay(1000);
analogWrite(9,val/8); //更に減速1秒間
delay(1000);
digitalWrite(11,LOW); //停止5秒間
delay(5000);
digitalWrite(10,HIGH); //低速発車5秒間
analogWrite(9,val/6);
delay(5000); // 低速発車後、確実にloopに戻して設定速度に移行させるための5秒
}
}


Arduino1年生にとっては、ここまで来てホッとしています。第2ステップ以降、なかなか進まないと思いますが、トライの都度 アップしようと思います。Arduinoのご経験豊富なブロガーの方々、1年生にアドバイスをよろしくお願いいたします。

×

非ログインユーザーとして返信する