- 追加された行はこの色です。
- 削除された行はこの色です。
#contents
*課題2: 黒い線に沿って動くロボットを作成せよ[#h9fee753]
各チームで交差点が2つ以上のコースを作成し、そのコースを3周するロボットを作成する。
交差点のうちの1つには500㎖の空の紙パックを置き、次のような動作をするプログラムを作成せよ。
1、紙パックを迂回する、あるいは紙パックを元の位置に戻した後コースに戻って進む。&br;
(交差点を通過後、紙パックが元の位置にあればよい。)&br;
2、紙パックを次の交差点まで運んでいき、その交差点に紙パックを残して更に黒い線に沿って進む。&br;
早さと正確さにも気をつけること。
*ロボットの概要[#z9f8aad6]
*コースの紹介 [#iae0b335]
#ref(course.jpg)&br;
交差点は3つにしました。&br;
カーブはできるだけ急にならないようにし、曲がりやすいようにしました。
*プログラム [#s8715280]
**迂回Ver. [#s874c7bf]
<その1>
#define THRESHOLD 40 //閾値の設定
#define turn_180 OnFwd(OUT_A);OnRev(OUT_C);Wait(130);Off(OUT_A+OUT_C);Wait(100); //180°回転の定義
task main (){
int i;
i = 0; //変数の設定
SetSensor(SENSOR_1,SENSOR_LIGHT); //センサー1=光センサー
SetSensor(SENSOR_2,SENSOR_TOUCH); //センサ−2=タッチセンサー
SetSensor(SENSOR_3,SENSOR_LIGHT); //センサ−3=光センサー
SetPower(OUT_A+OUT_C,2); //少しゆっくり動くように設定
Wait(100); //ボタンを押してからスタートするまで1秒待つ
while (i < 18){
if(SENSOR_1 > THRESHOLD){
if(SENSOR_3 > THRESHOLD){
OnFwd(OUT_A+OUT_C);
} //1も3も白=直進
else{
OnFwd(OUT_A);
Off(OUT_C);
} //1は白、3は黒=右折
}
else{
if(SENSOR_3 > THRESHOLD){
OnFwd(OUT_C);
Off(OUT_A);
} //1は黒、3は白=左折
else{ //1も3も黒だったら
Off(OUT_A+OUT_C);
Wait(100);
OnFwd(OUT_B);
Wait(50); //紙パックをつかむ
Off(OUT_A+OUT_C);
Wait(100);
OnFwd(OUT_A+OUT_C);
Wait(120); //少し前に出て
turn_180; //回転して
OnRev(OUT_B);
Wait(50); //紙パックを置く
OnRev(OUT_A+OUT_C); //少し下がって
Wait(80);
turn_180; //回転
i = i+1; //変数に1加える
}
}
}
if(SENSOR_2 == 1){ //タッチセンサーが反応したら
OnRev(OUT_A+OUT_C); //少し戻って..
Wait(100);
Off(OUT_A+OUT_C); //停止して相手が通り過ぎるのを待つ
Wait(300);
}
if(i == 18){ //交差点を18回(1周6回×3周)通過したら
Off(OUT_A+OUT_C); //自動的に停止
}
}
このプログラムはタッチセンサーがうまく反応しなかったときに作ったプログラムです。&br;
光センサーが両方とも黒に反応したとき、交差点とみなして紙パックをつかむようにしたのですが、&br;
これでは紙パックがない交差点でもつかむ動作をしてしまうのであまりいいプログラムではありません,,,&br;
そこでもう一つ、タッチセンサーに反応したらつかむ動作をするプログラムを作りました。&br;
途中までは<その1>と同じです。
#define THRESHOLD 40
#define turn_180 OnFwd(OUT_A);OnRev(OUT_C);Wait(150);Off(OUT_A+OUT_C);Wait(100);
task main (){
int i;
i = 0;
SetSensor(SENSOR_1,SENSOR_LIGHT);
SetSensor(SENSOR_2,SENSOR_TOUCH);
SetSensor(SENSOR_3,SENSOR_LIGHT);
Wait(100);
while (i < 3){
if(SENSOR_1 > THRESHOLD){
if(SENSOR_3 > THRESHOLD){
OnFwd(OUT_A+OUT_C);
}
else{
OnFwd(OUT_A);
Off(OUT_C);
}
}
else{
if(SENSOR_3 > THRESHOLD){
OnFwd(OUT_C);
Off(OUT_A);
}
else{
OnFwd(OUT_A+OUT_C);
}
}
}
if(SENSOR_2 == 1){ //タッチセンサーが反応したら
Off(OUT_A+OUT_C);
Wait(100);
OnFwd(OUT_B); //つかむ動作をする
Wait(50);
Off(OUT_A+OUT_C);
Wait(100);
OnFwd(OUT_A+OUT_C);
Wait(120);
turn_180;
OnRev(OUT_B);
Wait(50);
OnRev(OUT_A+OUT_C);
Wait(80);
turn_180;
i = i+1;
}
if(i == 3){
Off(OUT_A+OUT_C); //紙パックをつかむ動作を3回(1周1回×3周)で自動的に停止
}
}
<その2>は、光センサーが両方とも黒に反応したとき(普通の交差点)は直進、&br;
タッチセンサーが反応したとき(紙パックがある交差点)では紙パックをつかむ動作をするようにしました。&br;
1台だけで走らせるようだったのでもう一つのロボットを避けるプログラムは必要なかったので、&br;
タッチセンサーを紙パックに反応する方にまわしました。
**運搬Ver. [#obcaa8c3]
sub trace_head() //前にトレースするサブ
{ if((SENSOR_1>40)&&(SENSOR_3>40)){OnFwd(OUT_A+OUT_C);}
if((SENSOR_1>40)&&(SENSOR_3<40)){OnFwd(OUT_A);Off(OUT_C);Wait(1);}
if((SENSOR_1<40)&&(SENSOR_3>40)){OnFwd(OUT_C);Off(OUT_A);Wait(1);}}
sub trace_tail() //後ろにトレースするサブ
{ if((SENSOR_1>40)&&(SENSOR_3>40)){OnRev(OUT_A+OUT_C);}
if((SENSOR_1<40)&&(SENSOR_3>40)){OnRev(OUT_C);OnFwd(OUT_A);Wait(1);}
if((SENSOR_1>40)&&(SENSOR_3<40))OnRev(OUT_A);OnFwd(OUT_C);Wait(1);}
if((SENSOR_1<40)&&(SENSOR_3<40)){OnRev(OUT_A+OUT_C);}}
int across ; //交差点を渡った回数
task main(){
OnRev(OUT_B);Wait(50); //まず腕を開く
SetSensor(SENSOR_1,SENSOR_LIGHT);
SetSensor(SENSOR_2,SENSOR_TOUCH);
SetSensor(SENSOR_3,SENSOR_LIGHT);
across = 0 ;
while(across <=7) //交差点7回(=コース1周)するまで動く
{
/*++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/
trace_head();
if((SENSOR_1<=40)&&(SENSOR_3<=40)){across=across+1;Off(OUT_A+OUT_C);Wait(50);OnFwd(OUT_A+OUT_C);Wait(20);Off(OUT_A+OUT_C);Wait(80);}//交差点に着いたらカウントしてから乗り越える
if(SENSOR_2==1){Off(OUT_A+OUT_C);Wait(50);OnFwd(OUT_B);Wait(50);紙パックにぶつかったら腕で掴み、以下の作業を実行・・・
until((across ==2)||(across==4)||(across==8)||(across==10)|| (across==14)||(across==16)){ //紙パックを離すべき交差点に着くまで交差点をカウントしつつ進む
trace_head();
if((SENSOR_1<=40)&&(SENSOR_3<=40))
{ across =across+1;Off(OUT_A+OUT_C); Wait(50); OnFwd(OUT_A+OUT_C);Wait(20);Off(OUT_A+OUT_C);Wait(100);}
if((across ==2)||(across==4)||(across==8)||(across==10)|| (across==14)||(across==16)){ //紙パックを離す作業
ClearTimer(0);while(Timer(0) <10){trace_head();}Off(OUT_A+OUT_C);Wait(50);//交差点の前に出る
OnFwd(OUT_C);OnRev(OUT_A);Wait(60);while(SENSOR_3>40) {OnFwd(OUT_C);OnRev(OUT_A);}Off(OUT_A+OUT_C);Wait(50);//道を手探りしつつUターン
until((SENSOR_1<40)&&(SENSOR_3<40)) {trace_head();}Off(OUT_A+OUT_C);Wait(50);
ClearTimer(0);while(Timer(0) <=5){trace_tail();}Off(OUT_A+OUT_C);Wait(40);OnRev(OUT_B);Wait(50);
ClearTimer(0);while(Timer(0)<=6){trace_tail();} Off(OUT_A+OUT_C);Wait(50); //交差点の上に紙パックを置く
OnFwd(OUT_C);OnRev(OUT_A);Wait(60);while(SENSOR_3>40) {OnFwd(OUT_C);OnRev(OUT_A);}Off(OUT_A+OUT_C); Wait(50);
} //Uターンして元に戻る
}//kousaten
}//boxtukamu
}//while
}//taskmain
交差点に着いたとき、通り過ぎてからパックを後ろに置き去るようにしたのですが、Uターンが余りうまくいきませんでした。この調整に多くの時間がかかりました。
*反省、感想 [#cc226c18]
なかなかうまくいきませんでした。もっとプログラムを簡略化したり、ロボットを軽量化したり、できることがあったと思うので今後の課題に生かしたいと思いました。紙パックが思ったより軽くて思うようにタッチセンサーが働かなかったのですが、タッチセンサーの位置をもっと工夫すれば働いたと思います。紙パックをつかむモーター部分は本当によくできていました(相方に感謝!!)
*コメント [#hb8e1cd3]
コメントよろしくお願いします。
- センサーのif部分、実はもっとスリム化できます。センサーが白か黒か(もしくは触っていないか触っているか)を、その都度ifで判断するのではなく、「無反応なら0を、反応なら1を返す関数」を作ってみるといいかもしれません。 -- [[こさか]] &new{2009-07-02 (木) 21:57:24};
#comment