目次
課題3については2019a/Mission3を参照
基本的に、モーター二つを使って走る。LとL'については前に取り付けたアームでつかみ、プラ容器を右側に取り付けたアームでつかむ。プラ容器を持ち上げたまま、トレースをしていく。ボールを入れるプラ容器に沿って、車体を横向きにつけ、最後に、一気にプラ容器を持ち上げることで、車体の上を転がっていき、ボールをゴール地点のプラ容器の中に入れることができる。練習段階で、トレースをする際に車輪の幅が広くなってしまい、カーブが曲がりきれないことが多かった。そのためできる限りセンサーと車体の間隔を狭めることで、急なカーブにも対応できるようにした。また、センサー同士の幅を狭めたことで交差点でのトレースを正確に行えるようにした。前に取り付けたアームは、横から挟み込むようにボールをつかむ。センサーに当たらないように車体の前の方で上げ下げを行うが、重心が前にいき過ぎないよう工夫した。
#define BLACKS 38 #define BLACK 45 #define THRESHOLD 53 #define WHITE 60 #define WHITES 68 #define left_s OnFwd(OUT_A,60);OnRev(OUT_B,60); #define left OnFwd(OUT_A,60);Off(OUT_B); #define right_s OnFwd(OUT_B,60);OnRev(OUT_A,90); #define right OnFwd(OUT_B,60);Off(OUT_A); #define forward OnFwd(OUT_AB,60); #define back OnRev(OUT_AB,60); #define CONN 1 #define SIGNALON1 10 #define SIGNALOFF1 11 #define SIGNALON2 20 #define SIGNALOFF2 21 #define SIGNALON3 30 #define SIGNALOFF3 31 #define HALF 1900 #define QUARTER 220
left_s:両タイヤで左折 left:右タイヤで左折 right_s:両タイヤで右折 right:左タイヤで右折 forward:前進 back:後進
sub follow_line_left() //ラインの左側をトレースし、交差点で停止 { SetSensorLight(S1); SetSensorLight(S2); long t0=0,t1=0,stop_time=1;
while(t1-t0<stop_time){ if((SENSOR_1<BLACKS)&&(SENSOR_2<BLACKS)){ //二個のセンサーが黒を感知 t0=CurrentTick(); forward; until((SENSOR_1<THRESHOLD)&&(SENSOR_2<THRESHOLD)); //二個のセンサーが灰色を感知 t1=CurrentTick(); }else if(SENSOR_1<BLACKS){ left_s; }else if(SENSOR_1<BLACK){ left; }else if(SENSOR_1<THRESHOLD){ forward; }else if(SENSOR_1<WHITE){ right; }else if(SENSOR_1<WHITES){ right_s; } } Off(OUT_AB); Wait(1000); }
sub follow_line_right() //ラインの右側をトレースし、交差点で停止 { SetSensorLight(S1); SetSensorLight(S2); long t0=0,t1=0,stop_time=1;
while(t1-t0<stop_time){ if((SENSOR_1<BLACKS)&&(SENSOR_2<BLACKS)){ t0=CurrentTick(); forward; until((SENSOR_1<THRESHOLD)&&(SENSOR_2<THRESHOLD)); t1=CurrentTick(); }else if(SENSOR_2<BLACKS){ right_s; }else if(SENSOR_2<BLACK){ right; }else if(SENSOR_2<THRESHOLD){ forward; }else if(SENSOR_2<WHITE){ left; }else if(SENSOR_2<WHITES){ left_s; } } Off(OUT_AB); Wait(1000); }
sub follow_line_back() //ラインの右側をトレースし、交差点で停止 { SetSensorLight(S1); SetSensorLight(S2); long t0=0,t1=0,stop_time=1;
while(t1-t0<stop_time){ if((SENSOR_1<BLACKS)&&(SENSOR_2<BLACKS)){ t0=CurrentTick(); back; until((SENSOR_1<THRESHOLD)&&(SENSOR_2<THRESHOLD)); t1=CurrentTick(); }else if(SENSOR_2<BLACKS){ right_s; }else if(SENSOR_2<BLACK){ right; }else if(SENSOR_2<THRESHOLD){ back; }else if(SENSOR_2<WHITE){ left; }else if(SENSOR_2<WHITES){ left_s; } } Off(OUT_AB); Wait(1000); }
sub start_right()//右旋回 { right; Wait(100); }
sub start_left()//左旋回 { left; Wait(100); }
sub across()//ライン上をまっすぐ進み、外れると停止 { SetSensorLight(S1); SetSensorLight(S2); long t0=0,t1=0,stop_time=1;
while(t1-t0<stop_time){ if((SENSOR_1<BLACKS)&&(SENSOR_2<BLACKS)){ t0=CurrentTick(); forward; until((SENSOR_1<THRESHOLD)&&(SENSOR_2<THRESHOLD)); t1=CurrentTick(); }else if(SENSOR_1<WHITES){ forward; } } Off(OUT_AB); Wait(1000); } sub send_msg1()// { int msg; while(msg!=SIGNALOFF1){ SendRemoteNumber(CONN,MAILBOX1,SIGNALON1); ReceiveRemoteNumber(MAILBOX1,true,msg); }
}
sub send_msg2() { int msg; while(msg!=SIGNALOFF2){ SendRemoteNumber(CONN,MAILBOX2,SIGNALON2); ReceiveRemoteNumber(MAILBOX2,true,msg); } }
task main() { follow_line_left(); right_s; Wait(200); forward; Wait(900); Off(OUT_AB); send_msg1(); right_s; Wait(HALF); follow_line_right(); send_msg2(); }
#define CONN 1 #define SIGNALON1 10 #define SIGNALOFF1 11 #define SIGNALON2 20 #define SIGNALOFF2 21 #define SIGNALON3 30 #define SIGNALOFF3 31
sub ball_catch1()//前のアームでボールをつかみ、持ち上げる { OnFwd(OUT_A,40); Wait(200); OnRev(OUT_B,50); Wait(500); OnRev(OUT_A,60); Wait(700); Off(OUT_AB); }
sub ball_throw1()//ボールを持っていたアームを下げ、プラ容器の中に入れる { OnFwd(OUT_A,40); Wait(100); OnFwd(OUT_B,50); Wait(500); OnRev(OUT_A,60); Wait(700); Off(OUT_AB); }
sub ball_catch2()//プラ容器をつかむ { OnRev(OUT_C,50); Wait(150); Off(OUT_C); }
sub receive_msg1() { int msg; while(msg!=SIGNALON1){ ReceiveRemoteNumber(MAILBOX1,true,msg); //msgが空の間,MAILBOX1にmsgを受信し続ける } ball_catch1(); PlaySound(SOUND_UP); SendResponseNumber(MAILBOX1,SIGNALOFF1);//親機MAILBOX1にSIGNALOFF1を送る
}
sub receive_msg2() { int msg; while(msg!=SIGNALON2){ ReceiveRemoteNumber(MAILBOX2,true,msg); //msgが空の間,MAILBOX1にmsgを受信し続ける } ball_throw1(); PlaySound(SOUND_UP);//通信が成功したときの確認用 SendResponseNumber(MAILBOX2,SIGNALOFF2);//親機MAILBOX1にSIGNALOFF1を送る }
task main() { receive_msg1(); receive_msg2(); }
ロボットに関しては、早い段階で方向性が決まったことで、すぐに作り上げることができた。しかしプログラムに関してはあまり上手くいかず、ロボットの大きさや重さに合わせることが非常に難しかった。それでも練習段階で成功することができたので、そこから成功率を上げるための工夫が足らなかったと思う。本番に向けた対策を怠らなければ、今までやってきたことを遺憾なく発揮できたと思う。