今回は黒の線をライントレースするロボットを作りました

IMG_6807.JPG

概要

ロボット

IMG_6810.JPG

↑ロボットの全容  今回は紙コップをつかむためにコップの両側から挟み込むよう形にした。モーター三つ使い、二つはタイヤのモーターとして、もう一つはコップを掴むアームを回すために使用した。センサーはカラーセンサーだけを使い、RGBの値を読み取って30より大きいか小さいかで白か黒かを判断した。また、カラーセンサーがタイヤから離れてしまうと、後々誤差が大きくなってしまうため、なるべくタイヤから近い位置に取り付けるようにした。

コース

2018a-mission2.png

今回は上記もコースを下記のようなルートでライントレースをした

1.Aをスタート
2.Bを直進
3.Cで一時停止の後、直進
4.Dで一時停止の後、Xの空き缶をキャッチしてD地点に戻る
5.DからEに向かい、Eを直進
6.Fを左折
7.Gで一時停止の後、左折
8.Hで一時停止の後、右折
9.Iで一時停止の後、右折
10.Lを直進
11.Kを直進
12.Jで一時停止の後、空き缶をYに置きてJに戻りBに向かう
13.Bで一時停止の後、左折
14.Aで停止

プログラミング

ライントレース

 今回は黒の線に対して左側をジグザグに指定した時間動き、その後白か黒の継続時間によって停止するようにしたものと右側を同様に動く二つの主となるプログラムを作った。  これによって、前半は前者のプログラムを、後半は後者のプログラムを使うことで他のプログラムを関数なしの大雑把なプログラムで解決することが出来た。  試行錯誤を繰り返している最中にどうしても継続時間がカーブで長くなってしまい、止まってしまった。そこで、ある時間まではひたすらコースを逸れずに同じ色の領域にいても線の境界に無理矢理にでも戻るようにした。   線の境界が左側のプログラム(tが境界に居続ける時間、sがt秒以降、s秒以上同じ色の領域にいると止まる。)

def sharpstop_line(t,s):
 t0 = time.time()
 t1 = time.time()
 while t0 - t1 < t:
       t0 = time.time()
       if cs.value() <=30:
        while cs.value() <=30:
                  ml.run_forever(speed_sp= -25)
                  mr.run_forever(speed_sp= 100)
       elif cs.value() >30:
        while cs.value() >30:
                    ml.run_forever(speed_sp= 100)
                    mr.run_forever(speed_sp= -25)
 ml.stop()
 mr.stop()
 s0 = time.time()
 s1 = time.time()
 while s0 - s1 < s:
      s1 = time.time()
      if cs.value() <=30:
         while cs.value() <=30:
                  ml.run_forever(speed_sp= 100)
                  mr.run_forever(speed_sp= -25)
                  s0=time.time()
      elif cs.value() >30:
           while cs.value() >30:
                    ml.run_forever(speed_sp= -25)
                    mr.run_forever(speed_sp= 100)
                    s0=time.time()
 ml.reset()
 mr.reset()
 sleep(1)

線の境界が右側のプログラム(tが境界に居続ける時間、sがt秒以降、s秒以上同じ色の領域にいると止まる。)

def rev_sharpstop_line(t,s):
 t0 = time.time()
 t1 = time.time()
 while t0 - t1 < t:
       t0 = time.time()
       if cs.value() <=30:
        while cs.value() <=30:
                  ml.run_forever(speed_sp= 100)
                  mr.run_forever(speed_sp= -25)
       elif cs.value() >30:
        while cs.value() >30:
                    ml.run_forever(speed_sp= -25)
                    mr.run_forever(speed_sp= 100)
 ml.stop()
 mr.stop()
 s0 = time.time()
 s1 = time.time()
 while s0 - s1 < s:
      s1 = time.time()
      if cs.value() <=30:
         while cs.value() <=30:
                  ml.run_forever(speed_sp= -25)
                  mr.run_forever(speed_sp= 100)
                  s0=time.time()
      elif cs.value() >30:
          while cs.value() >30:
                    ml.run_forever(speed_sp= 100)
                    mr.run_forever(speed_sp= -25)
                    s0=time.time()
 ml.reset()
 mr.reset()
 sleep(1)

交差点での動作

def right():#右折
   ml.run_timed(time_sp = 500,speed_sp =100,stop_action ='brake')
   mr.run_timed(time_sp = 500,speed_sp =-100,stop_action ='brake')
   sleep(1)
def left():#左折
   ml.run_timed(time_sp = 500,speed_sp =-100,stop_action ='brake')
   mr.run_timed(time_sp = 500,speed_sp =100,stop_action ='brake')
   sleep(1)
def forward():#直進
   ml.run_timed(time_sp = 500,speed_sp =100,stop_action ='brake')
   mr.run_timed(time_sp = 500,speed_sp =100,stop_action ='brake')
   sleep(1)

紙コップの処理

def cop_catch():#コップを掴む
ml.stop()
mr.stop()
ma.reset()
ma.run_timed(time_sp=2000,speed_sp=-100,stop_action='hold')
sleep(3)
def cop_throw():#コップを放す
ml.stop()	
mr.stop()
ma.reset()
ma.run_timed(time_sp=2000,speed_sp=100,stop_action='brake')
sleep(3)

実際の動作

sharpstop_line(0,0.7)#1の動作
sleep(1)
right()
right()
sharpstop_line(34,0.6)#2.3の動作
cop_catch()#4の動作
left()#5の動作
left()
sharpstop_line(2.5,0.7)
right()#6の動作
sharpstop_line(9,0.7)
left()#7の動作
sharpstop_line(1.5,0.65)
sleep(1)
left()#8の動作
sharpstop_line(38,0)
sleep(1)
right()
right() 
rev_sharpstop_line(2,0.75)
sleep(1)
rev_sharpstop_line(3,0.75)#9の動作
sleep(1)
right()
rev_sharpstop_line(2,0.75)#10の動作
left()
left()
rev_sharpstop_line(2,0.75)#11の動作
left()
left()
rev_sharpstop_line(2,0.75)#12の動作
sleep(1)
left()
left()
left()
left()
left()
left()
cop_throw() 
left()#13.14の動作
left()
left()
left()
left()
left()
rev_sharpstop_line(4,0.75)
sleep(1)
left()
left()
left()
forward()
rev_sharpstop_line(3,0.75)

あえてright()、left()、forward()の車体の動く大きさを大きくしてある。また、領域内にいて良い時間も長くしてある。そのため、コースの途中で間違って止まることが格段に減ったが、その分車体がコースと90°くらいに曲がってしまうが、right()、left()の値が大きく設定され、かつ次のsharpstopでは白の領域にさえ入ってしまえば、いくらでも修正してくれるので少ないプログラムで済んだ。

総括

前回に比べ、かなり簡潔なプログラムが出来たと思う。その分sharpstopのプログラムに行き着くまでが長くなってしまい、かなり時間がぎりぎりになってしまった。成功率は最後にはほぼ100%にまで持って行けたのでそこは良かった。


添付ファイル: fileIMG_6810.JPG 176件 [詳細] fileIMG_6807.JPG 142件 [詳細] file2018a-mission2.png 126件 [詳細]

トップ   編集 凍結 差分 履歴 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS
Last-modified: 2018-08-12 (日) 20:50:19