2016b/Member 目次
課題2の二番目の経路を想定した。
B地点をスタートしてQ付近の3/4円周上でピンポン玉をつかみ、そのピンポン玉をC地点においたゴールへシュートする (二人目) Bスタート → R直進 → P右折 → Q直進 → (ピンポン玉をキャッチ) → Q直進 → R右折 → P直進 → S右折 → Cへシュート
ロボット本体は四輪で黒線の端を縫うようにトレースする。ボールは二つのアームでとらえる。本体は小さい方が望ましい。
四輪型で少しコンパクトにし、また大きい方のタイヤを前輪にすることで細かい動きができるようにした。光センサーはロボットの前側に取り付けた(右の画像)。できるだけ光センサーをタイヤに近い位置にとりつけるようにした。
クワガタムシのように側面からはさみこむような構造にした。ロボット本体の前面に取り付けた。まずロボット本体の前側に光センサーをつけ、さらにそこにアームをつける形になった。
#define mid 49 // 明るさの閾値。この値を基準にして、光センサーが示す値に応じて五段階で旋回やカーブを行う #define cuvright() Off(OUT_AC);OnFwd(OUT_A); #define cuvleft() Off(OUT_AC);OnFwd(OUT_C); // 左右にカーブする #define turnright() Off(OUT_AC);OnFwd(OUT_A);OnRev(OUT_C); #define turnleft() Off(OUT_AC);OnFwd(OUT_C);OnRev(OUT_A); // 左右に旋回 #define cls Off(OUT_ABC);SetPower(OUT_B,2);OnFwd(OUT_B);Wait(15);Off(OUT_B); // ハサミ(アーム)閉じ #define opn Off(OUT_ABC);SetPower(OUT_B,2);OnRev(OUT_B);Wait(15);Off(OUT_B); // ハサミ開け #define clag SetPower(OUT_B,2);OnFwd(OUT_B);Wait(5);Off(OUT_B); // ハサミ閉めなおし #define opnf SetPower(OUT_B,2);OnRev(OUT_B);Wait(15);Off(OUT_B); // ラストのハサミ開け
task main() { SetSensor(SENSOR_2,SENSOR_LIGHT); ClearTimer(0); int c=0; int t=0; // tは時間、cは交差点or丁字路カウント
:::
ここからラインのトレースのプログラム
:::
// 交差点カウントが一定以上になったとき、つまり経路が終わるときこのループを抜ける while(c<=6){ // 一定時間以上ロボットが曲がったとき、交差点と判断してこのループを抜ける。曲がり時間の測定はFastTimer(0)で行なっている while(FastTimer(0)<=24){ OnFwd(OUT_AC); ClearTimer(0);
// センサーが明るいところを通っている時右旋回 if(SENSOR_2>mid+3){ turnright() until(SENSOR_2<=mid-3); Off(OUT_AC); ClearTimer(0); // ある程度暗いところまで達するまで曲がるのをやめない。以降も同様にuntilを用いて記述している }
// やや明るいところを通っている時右カーブ else if(SENSOR_2>mid+1){ cuvright() until(SENSOR_2<=mid-3); Off(OUT_AC); ClearTimer(0); }
// 白と黒の境目を通っている時直進 else if(SENSOR_2>=mid){ClearTimer(0);}
// やや暗いところを通っている時左カーブ else if(SENSOR_2>mid-4){ ClearTimer(0); cuvleft() until(SENSOR_2>=mid+3); Off(OUT_AC); }
// 暗いところを通っている時左旋回 else { turnleft() ClearTimer(0); until(SENSOR_2>=mid+4); Off(OUT_AC); } }
:::
ここまでがラインのトレース。以降のプログラムは交差点の動作
:::
// 二つ目の方のwhileを抜けたら、つまり交差点あるいは丁字路にさしかかったら、cの値に応じて直進、右折をそれぞれ行う。 // cの値は交差点丁字路を過ぎる度に1増え、次の交差点に対応する。交差点での動作が終わったら、ループに戻る
t=FastTimer(0); // 交差点丁字路にさしかかったらまず、直進右折といった行動の前に交差点丁字路に対してなるべく進入する前に近い方向に向かせる turnright(); Wait(t);
// 以下が各交差点、丁字路の通過の動作
// P地点を右折 if(c==0){ Off(OUT_ABC); Wait(100); turnright(); Wait(40); OnFwd(OUT_AC); Wait(25); c=c+1; ClearTimer(0);}
// Q直進し、ボールをつかむ else if(c==1){ Off(OUT_ABC); Wait(100); turnleft(); Wait(10); OnFwd(OUT_AC); Wait(50); cls; c=c+1; ClearTimer(0);}
//Q直進 else if(c==2){ Off(OUT_ABC); Wait(100); turnleft(); Wait(5); OnFwd(OUT_AC); Wait(50); c=c+1; ClearTimer(0); }
// R右折 else if(c==3){ OnFwd(OUT_AC); clag; Wait(40); turnright(); Wait(50); until(SENSOR_2>=mid-4); Off(OUT_AC); c=c+1; ClearTimer(0); }
// P直進 else if(c==4){ Off(OUT_ABC); Wait(100); turnleft(); Wait(5); OnFwd(OUT_AC); Wait(50); c=c+1; ClearTimer(0); }
// S右折 else if(c==5){ OnFwd(OUT_AC); clag; Wait(40); turnright(); until(SENSOR_2>=mid-4); Off(OUT_AC); c=c+1; ClearTimer(0); }
//ラスト、ボールをゴールへ押し出す else if(c==6){ turnleft(); Wait(10); OnRev(OUT_AC); Wait(70); OnFwd(OUT_AC); Wait(60); opnf; c=c+1; ClearTimer(0); Off(OUT_ABC); } } }
光センサーの値に応じて五段階で対応を変化させるようにした。基本的に黒線の左の方を縫うように移動するよう想定した。カーブまたは旋回するときはuntilを用い一定の明るさになるまで曲がるのをやめないようにした。旋回やハサミの開閉といった動作は、プログラムを簡略化するためマクロで定義した。
変数を用い、交差点や丁字路にさしかかったときに経路通り進むよう交差点ごとに対応を変えるようにした(使った変数はプログラム中のc)。
光センサーでの交差点か丁字路かの判定は行わず、経路中で交差点か丁字路かのどちらかを見つけたら、変数を使いそれが何個目のカーブかで判断させるようにした
ボールを掴んで経路を進むときにアームがゆるみボールをつかまえたままにできなかったので、交差点にさしかかったときに二度ほどアームを閉めなおしてボールをつかんだままでいられるようにしようとした。
経路通りに進みボールをとらえることはできたが、アームの閉めなおしを行なってもまだボールをこぼしてしまうことがあった。アームの閉め直しの頻度を上げれば解決できた可能性があったが、試す時間が無く断念した。また今回の課題は発表の時までに終えることができなかった。
例えばロボットを前進させたいときにwhile(true){OnFwd(OUT_AC);}というようなプログラムを実行させたとき、前進の速度が明らかに遅いということがあった。なぜかは分からなかったが、今後このような動作をさせることは避けたい、
前回よりは思い通り動作を行える形にすることができたが、最後までしっかり終えられることができなかったのが残念だった。また、このプログラムで動かしたときのトレースは小刻みに黒線の境を旋回しながらあまりスムーズに進まず、効率的でない進み方に思えたがこれも時間が足らず改善することができなかった。
完璧には程遠い結果であったが、試行錯誤を重ねたことである程度は要領を学ぶことができたように思える。次回の課題へ活用したい。