#contents
*課題目的 [#v69fdd5a]
今回の課題の目的は下の図のようなコースを作成し、「ミッション」を遂行するためのロボットを作成する。
#ref(2017b/Member/tono/Mission2/コース説明.png,center,75%,コース説明)
私のコースはAだったから上の図のようにオレンジ色の矢印の順番に沿って動くロボットを制作した。ただし緑色のところは紙コップを取得すると置く操作ことである。
*ロボットについて [#m7f2d6cc]
**ロボット全体 [#q6260e78]
#ref(2017b/Member/tono/Mission2/ロボット説明1.png,center,75%,ロボット説明)
ロボットを作る前にグループの中で様々なことを考えた。例えば、光センサーをつける場所、紙カップをとる部分の構造、などである。結局、上の図のようにロボットを作った。ロボットを正確に動くため光センサーをつける場所はできるだけ床に近いである。
**紙カップを取る部分 [#u6a04e60]
#ref(2017b/Member/tono/Mission2/ロボット説明2.png,center,75%,ロボット説明)
また、紙カップを取る部分の構造上の図である。紙カップをとる部分の構造は紙カップより大きく作った。なぜなら、取るときに紙カップが入るようになるためである。また、紙カップを取る部分が上げ下げるときにはできるだけ滑らかに動くため2つのモータを使った。ただし、図のようにモータは紙カップを取る部分の左側と右側にある。
*プログラムについて [#l6fe72bd]
 コース上に動けるようになるためにはLine Traceを使った。Line Traceのプログラムでは資料の練習問題49と同様に5段階(白い、白いと境界付近の間、境界付近、黒いと境界付近の間、黒い)を使ってロボットを動く。そのためには5段階の明るさを実際にコースの上で測定しなければならない。5つの測定できた値は以下のものである;
|CENTER:段階|CENTER:白い|CENTER:白いと境界付近の間|CENTER:境界付近|CENTER:黒いと境界付近の間|CENTER:黒い|
|CENTER:明るさ値|CENTER:52以下|CENTER:45−52|CENTER:38−45|CENTER:33−38|CENTER:33以上|
次に、段階によって違う動くを考えましょう。下の図のように(A)と(B)の場合によってコースに戻る方法が違う。
#ref(2017b/Member/tono/Mission2/ton1.png,center,75%,line Trace)center
**(A)のときのLine Trace プログラム [#v8123131]
まず(A)の場合は白くなったら右側に戻る動く。そのことから5段階の明るさを使って左側と右側のモータのスピードによってロボットを動く。(注意:左側のモータが正のスピードのとき右に曲がる、右側のモータのスピードが正のとき左に曲がる。負のスピードの場合は逆)みぎ5段階の明るさとモータのスピードは以下のものである;
|CENTER:段階|CENTER:方向|CENTER:(左側モータのスピード、右側モータのスピード)|
|CENTER:白い|CENTER:左旋回|CENTER:(SPEED_CURVE,-SPEED_CURVE)|
|CENTER:白いと境界付近の間|CENTER:左折|CENTER:(SPEED_TURN,0)|
|CENTER:境界付近|CENTER:直進|CENTER:(SPEED_STRAIGHT,SPEED_STRAIGHT)|
|CENTER:黒いと境界付近の間|CENTER:右折|CENTER:(0,SPEED_TURN)|
|CENTER:黒い|CENTER:右旋回|CENTER:(-SPEED_CURVE,SPEED_CURVE)|
ただし、SPEED_STRAIGHT=30,SPEED_CURVE=30,SPEED_TURN=40 のときロボットがうまくLine Traceできるから個の値を使った。
説明したものより(A)のときのLine Trace のプログラム以下のようになる。
-マクロの説明
 #define THRESHOLD 45 //しきいの値
 #define SPEED_STRAIGHT 30  
 #define SPEED_CURVE 30
 #define SPEED_TURN 40
 #define OnRL(speedR,speedL) OnFwd(OUT_A,speedR);OnFwd(OUT_B,speedL);
 #define go_forward OnRL(SPEED_STRAIGHT,SPEED_STRAIGHT);  //直進
 #define turn_left0 OnRL(SPEED_CURVE,-SPEED_CURVE);  //左旋回
 #define turn_left1 OnRL(SPEED_TURN,0);  //左折  
 #define turn_right1 OnRL(0,SPEED_TURN);  //右折    
 #define turn_right0 OnRL(-SPEED_CURVE,SPEED_CURVE);  //右旋回
-subスクリプトの説明 このプログラムはLine Traceと交差点判断は一緒に行う。もし、交差点かどうか判断するための時間(今回は150とする)より長くなって黒くなったら、それは交差点と判断して一回音を出すようにした。一方、黒くなかったら時間をリセットする。
 sub moveA1()                  //(A)のときのLine Trace 
 {
     SetSensorLight(S1);                   //端子は1番である
     long t0=CurrentTick();
     while(CurrentTick()-t0<150){         //時間が150以下のとき繰り返す
     while(CurrentTick()-t0<150){         //時間が150以下のとき
     if (SENSOR_1 < THRESHOLD -12) {      //黒いなら
     turn_right0;                         //右旋回
     }else{                                    
     t0=CurrentTick();            //時間リセット
     if (SENSOR_1 < THRESHOLD -7) {       //黒いと境界付近の間なら
     turn_right1;                     //右折
    } else if (SENSOR_1 < THRESHOLD +7) {   //黒いと境界付近の間
     go_forward;                     //直進
    } else if (SENSOR_1 < THRESHOLD +12) {  //白いと境界付近の間なら
     turn_left1;                     //左折
    } else {                  //白いなら
     turn_left0;               //左旋回
    }
    }
    }
     PlaySound(SOUND_LOW_BEEP);       //音を出す
 }
しかし、このsubスクリプトでは急なカーブのところでは交差点に判断したりしなかったりすることが問題だった。そのため、交差点かどうか判断するための時間を延ばして問題が解決できるようになった。
 sub moved(int d)
しかし、このsubスクリプトでは急なカーブのところでは交差点に判断したりしなかったりすることが問題だった。そのため、交差点かどうか判断するための時間を延ばして問題が解決できるようになった。下のsubスクリプトのように交差点かどうか判断するための時間をdとし、時間dは違うカーブによって設定できる。
 sub moveA2(int d)
 {
     SetSensorLight(S1);
     long t0=CurrentTick();
     while(CurrentTick()-t0<d){
     while(CurrentTick()-t0<d){            //時間がd以下のとき繰り返す
     if (SENSOR_1 < THRESHOLD -12) {
     turn_right0;
     } 
     else{
     if (SENSOR_1 < THRESHOLD -7) {
     turn_right1;
    } else if (SENSOR_1 < THRESHOLD +7) {
     go_forward;
    } else if (SENSOR_1 < THRESHOLD +12) {
     turn_left1;
    } else {
     turn_left0;
     }
     }
     }
     PlaySound(SOUND_LOW_BEEP);
     short_break; 
 }

**(B)のときのLine Trace プログラム [#c9fff65d]
(B)のときのLine Trace プログラム は(A)のときの反対側に動く。subスクリプトを書くときにただ左と右と右から左を変える。だから(A)のときと同じように2つsubスクリプトは以下のものである:
 sub moveB1()
 {
     SetSensorLight(S1);
     long t0=CurrentTick();
     while(CurrentTick()-t0<150){
     if (SENSOR_1 < THRESHOLD -12) {
     turn_left0;
     } 
     else{
     t0=CurrentTick();
     if (SENSOR_1 < THRESHOLD -7) {
     turn_left1;
    } else if (SENSOR_1 < THRESHOLD +7) {
      go_forward;
    } else if (SENSOR_1 < THRESHOLD +12) {
      turn_right1;
    } else {
      turn_right0;
     }
     }
     }
    PlaySound(SOUND_LOW_BEEP);
  }

(B)のとき時間kは違うカーブによって設定できる
 sub moveB2(int k)
 {
     SetSensorLight(S1);
     long t0=CurrentTick();
     while(CurrentTick()-t0<k){
     if (SENSOR_1 < THRESHOLD -12) {
     turn_left0;
    } else{
     if (SENSOR_1 < THRESHOLD -7) {
     turn_left1;
   } else if (SENSOR_1 < THRESHOLD +7) {
      go_forward;
   } else if (SENSOR_1 < THRESHOLD +12) {
      turn_right1;
   } else {
      turn_right0;
     }
     }
     }
     PlaySound(SOUND_LOW_BEEP);
  }


トップ   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS