- 追加された行はこの色です。
- 削除された行はこの色です。
#contents
ホーム[[2017b/Member]]
*1課題 [#hfe78483]
下の図のようなコースを各チームで作成し、「ミッション」を遂行するためのロボットを作成せよ。
** コース [#o4d47308]
黒線の幅は20mmでなるべく均等な濃さにすること。なお図の中の寸法の単位はcmで、黒線についてはその真ん中からの距離である。
#ref(2017b/Mission2/2017b-mission2.png,80%,課題2のコース)
** ミッション [#g924da6d]
次のいずれかのコースで黒い線に沿って動き、紙コップを移動させるロボットを製作せよ。
(相棒と違うコースを選ぶこと。ただし第3コースは3名チーム用とする。)
**選択したコース [#g232e8c2]
第1コースを選びました。
*** 第1コースの内容 [#x04ca08e]
+ Aをスタート
+ Bを直進
+ Cを右折
+ Fを直進
+ Rを左折(一時停止)
+ Pを直進
+ X地点の紙コップを取得してコースに戻る
+ Qを左折
+ Sを直進(一時停止)
+ Y地点に紙コップを置いてコースに戻る
+ Sを直進(一時停止)
+ Fを左折(一時停止)
+ Cを右折(一時停止)
+ D地点へ(ゴール)
*2ロボットの紹介 [#hfe78483]
基本のロボットに光センサーとアーム、起動スイッチを付けた構造になっています。
**ロボットの形 [#n402669d]
&ref(2017b/Member/Yoshi/Mission1/ko-zenntaizu.jpg,50%,子の全体像);
&ref(2017b/Member/Yoshi/Mission1/dodai-zenntai.jpg,87%,土台の全体像);
&br;
右のロボットが土台となりX軸方向に自由に移動できる。
&br;
左のロボットが土台のレールにのり、レール上をY軸方向に移動したり、筆ペンを上下に動かす。
&ref(2017b/Member/Yoshi/Mission2/rosoku.JPG,60%,ロボの全体像1);
&ref(2017b/Member/Yoshi/Mission2/rozennpou.JPG,60%,ロボ全体像2);
&ref(2017b/Member/Yoshi/Mission1/robo-zenntai.jpg,90%,全体像);
&br;
完成形は上図のようになっています。
X方向には無制限に動けますがY方向にはレールの長さ分のみしか動けません。しかし今回はA4の紙に字を書くということで紙の短辺をロボットのY方向にすることで問題を回避しました。
*3ロボット作成で工夫した点 [#r3f47f32]
**土台部分(X軸) [#w709e2dc]
&ref(2017b/Member/Yoshi/Mission1/dodai-yokohaba.jpg,70%,全体像);
&ref(2017b/Member/Yoshi/Mission2/rozenn.JPG,60%,ロボの全体像(前方から)3);
ロボットの安定性を高めるためにタイヤの間隔をひろくとりました。またモーターにタイヤを二つ取り付けることで二輪駆動を実現しています。
光センサーと紙との距離を適切に設定することで取得する数値の安定化を図りました。
**上部(Y軸、ペンの上下) [#k25b8768]
&ref(2017b/Member/Yoshi/Mission1/ko-hukann.jpg,70%,全体像);
&ref(2017b/Member/Yoshi/Mission1/ko-pen.gif,43%,ペンの機構);
またロボットの左側に接触センサーを取り付け、起動ボタンとして活用しました。
参考サイトに習い、上部の安定性を向上するために、レールの内側と同じ幅で突起を取り付けました。
また筆ペンの上下機構がレール上からずれていてバランスが悪いために反対側に重りとしてタイヤを付けました。
2枚目の画像のようにペンを上下する機構はモーターの回転する動きからウォームギアで上下の動きに変換しています。
*4プログラム [#t1f283c1]
**定義した定数 [#o1329b1a]
プログラムを簡略化し、開発しやすくするためにいくつか定数を定義しました。
&br;
以下はその抜粋です
#define Apower 35
#define Bpower 34
#define Ytime 1624 //y軸で10cm進むのに必要なおおよその時間
#define gotime 1692 //x軸で10cm進むのに必要なおおよその時間
#define bai 0.8 //文字を書く倍率
解説が必要なのは少ないでしょうが、まず上二つが移動用モーターの出力です。AがX軸でBがY軸に対応しています。数値が違うのは特に意味はりません。ただ全力で動かずかつ弱すぎない出力にしました。
&br;
次の二つはそれぞれの方向で定義した出力で動かした際に10cm進むのにかかる時間(ms)です。電池の消耗とモーターの個性に簡単に対応できるようにするために作りました。
&br;
最後の定数の「bai」は文字を書く際の倍率です。プログラム上のすべてのモーターの駆動時間にbaiをかけることで簡単に文字の大きさを調整できます
#define Apower 37
#define Bpower 34 //直進するのに必要な出力
#define ttime 950 //90度曲がるのに必要な時間
#define kanndo 30 //感度、ライントレースの反応の度合い
解説が必要なのは少ないでしょうが、まず上二つが移動用モーターの出力です。数値を左右で変えてまっすぐ先進するようにしました。
3つめは旋回時に90°回転するための待ち時間です。
最後の『kanndo』はライントレースの感度です。
**定義したサブ関数 [#m9587eea]
定数と同様にいくつかサブ関数を定義しました。これにより可読性を高め、他人が見てもわかりやすくなります。
&br;
以下はその抜粋です
sub go_forX(float t)
サブ関数の中には中にサブ関数を使用しているところがあるので分けて説明します。
***サブ関数その1 [#n49e72fe]
sub go_for()
{
OnFwd(OUT_A,Apower);
Wait(t*gotime*bai);
Float(OUT_AB); //前進X(t×10)cm
Wait(1000);
OnFwd(OUT_B,Bpower);
}
sub go_backX(float t)
sub go_back()
{
OnFwd(OUT_A,-Apower);
Wait(t*gotime*bai);
Float(OUT_AB); //後進X(t×10)cm
Wait(1000);
}
sub go_forY(float t)
{
OnFwd(OUT_B,-Bpower);
Wait(t*Ytime*bai);
Float(OUT_AB); //前進Y(t×10)cm
Wait(1000);
}
sub go_backY(float t)
sub turnL(float c)
{
OnFwd(OUT_B,Bpower);
Wait(t*Ytime*bai);
Float(OUT_AB); //後進Y(t×10)cm
Wait(1000);
OnFwd(OUT_A,Apower);OnFwd(OUT_B,-Bpower);
Wait(c*ttime);
Float(OUT_AB); //左に曲がる(c×90)度
}
sub penup()
sub turnR(float c)
{
RotateMotor(OUT_C, 10,50);
Wait(1500);
Off(OUT_C); //ペンを上げる
OnFwd(OUT_A,-Apower);OnFwd(OUT_B,Bpower);
Wait(c*ttime);
Float(OUT_AB); //右に曲がる(c×90)度
}
sub pendown()
ここで上げたサブ関数はロボットを動かす基本動作です。先進、後進、右旋回、左旋回のためのサブ関数です。前進、後進は開始のみ、旋回は回転する角度を指定して旋回します。
***サブ関数その2 [#zb1341d5]
sub turnR2(float d)
{
RotateMotor(OUT_C, -10,50);
Wait(1500);
Off(OUT_C); //ペンを下げる
OnFwd(OUT_A,Apower-d*kanndo);OnFwd(OUT_B,Bpower+d*kanndo);
}
sub go_XY(float t)
sub turnL2(float d)
{
OnFwd(OUT_B,-Bpower);
OnFwd(OUT_A,Apower);
Wait(t*Ytime*bai);
Float(OUT_AB); //斜めYは(t×10)cm
Wait(1000);
penup();
OnFwd(OUT_B,Bpower);
OnFwd(OUT_A,-Apower);
Wait(t*Ytime*bai);
Float(OUT_AB);
Wait(1000);
OnFwd(OUT_A,Apower+d*kanndo);OnFwd(OUT_B,Bpower-d*kanndo);
}
sub go_XY2(float t)
sub turnR1(float d)
{
OnFwd(OUT_B,-Bpower);
OnFwd(OUT_A,-Apower);
Wait(t*Ytime*bai);
Float(OUT_AB); //斜めYは(t×10)cm
Wait(1000);
penup();
OnFwd(OUT_B,Bpower);
OnFwd(OUT_A,Apower);
Wait(t*Ytime*bai);
Float(OUT_AB);
Wait(1000);
OnFwd(OUT_A,-d*kanndo);OnFwd(OUT_B,Bpower+d*kanndo);
}
sub turnL1(float d)
{
OnFwd(OUT_A,Apower+d*kanndo);OnFwd(OUT_B,-d*kanndo);
}
定義したサブ関数は大きく分けてペンを所定の位置に動かすもの(go_forX、go_backX、go_forY、go_backY、go_XY、go_XY2)とペンを上下するもの(penup、pendown)に分かれます。
&br;
まず所定の位置に動かすものは、すべて変数tがモーターの駆動として設定されています。t=1,bai=1の時においてXYどちらも10cm程動くようになっているためtをいくつにするかで進む距離を決定できます。
&br;
またロボットが動いたとは機体が揺れることを考慮して1秒の待機時間を入れてあります。
可
「go_XY、go_XY2」はペンが斜めに移動する用の関数です斜めに移動して戻ってくるところまでがセットになっています。
ここで上げたサブ関数はライントレースをする際に使います。黒線と白線の境界からのずれを『d』としてずれに応じて
ペンを上下するものは単純です。モーターを特定の角度だけ回転させる関数でペンの上下をしています。
**実行するプログラム [#t144e1c4]
ここまでで定義したものを使って「埼玉」と書くために以下のようにtask mainを作りました
task main ()
{
ResetTachoCount(OUT_C);
penup();
go_backY(0.9); //調整1
pendown();
go_backX(0.5); //よこ(土)
penup();
go_forY(0.3);
pendown();
go_forX(0.5); //よこ
penup();
go_backX(0.25); //よこ
pendown();
go_backY(0.5); //縦
penup();
go_backX(0.6);//移動to大
go_backY(0.4);
pendown();
go_forY(0.2); //たて()大
go_XY(0.25); //斜め1
pendown();
go_XY2(0.25); //斜め2
go_forX(0.25);
pendown();
go_backX(0.5); //横(大)
penup();
go_forY(0.5); //移動to可
go_forX(0.4);
pendown();
go_backX(0.5); //可はじめ
go_forY(0.5);
penup();
go_forX(0.4);
go_backY(0.1);
pendown();
go_backY(0.3); //口
go_backX(0.3);
go_forY(0.3);
go_forX(0.3);
penup();
go_backX(0.9); //移動to(玉)
go_forY(0.5);
go_backY(0.3);
pendown();
go_backY(1.2);// |
penup();
go_forX(0.3);
pendown();
go_backX(0.6);// --
penup();
go_forY(0.6);
pendown();
go_forX(0.6);// --
penup();
go_forY(1);
go_backY(0.3);
pendown();
go_backX(0.6);// --
penup();
go_forX(0.2);
go_backY(0.4);
pendown();
go_XY2(0.25);//斜め(玉)
penup();
}
特出して書くことはないと思いますが、「埼」から「玉」に移動する際にY軸の位置をレールの端に合わせてずれにくいようにしています
*5実行結果 [#yce51899]
こうして作ったロボットとプログラムを動かしてみた。まず倍率を0.8倍にして動かした。
&br;
その結果
&ref(2017b/Member/Yoshi/Mission1/kekka1.jpg,87%,埼玉1);
&br;
のように最後の一画が少しはみ出た。なので今度は倍率を0.5倍にして動かした。
&br;
その結果
&ref(2017b/Member/Yoshi/Mission1/kekka2.jpg,87%,埼玉1);
&br;
となりはみ出ずに書くことができた。