上肢帯のあるロボット5


毎週少しずつアップデートを重ねている”上肢帯のあるロボット”ですが、
先週、制御周期がWindowsの上限で20Hzが限界かも、と書きました。

これは、1往復につきドライバの問題で2msecのディレイが発生するため22個のサーボで、送受信を行うと、トータル46msecの時間がかかるというものでした。

この問題に対して、Facebookにて、

各サーボの返信ディレイ時間をID順に遅く設定して、全サーボに一斉送信でリターンパケット要求をすると、制御周期を早くできる(かも)

というコメントをいただいたので、さっそく試してみることにしました。

概念としてはこんな感じで、ID:0xFFで、全体送信するパケットに、応答要求を仕込みます。
デフォルトのサーボでは、全サーボが同時に返答してしまい、パケットが混信するのですが、各サーボのレスポンスタイムを少しずつずらして、順番に返事を受け取ろうという作戦です。

問題は、2つあり

  1. そもそも、0xFFの送信に対して、サーボが応答するのか
  2. 応答したとして、ずらすレスポンスタイムは何μsecが適正なのか

というところです。

どちらの問題も試してみて答えを見つける他ありません。

「1」の問題はすぐ解決しました。
1個のサーボを試してみたところ、返答がありました。

「2」に関しては試行錯誤しかありません。
次の画像が試行錯誤の結果です。

1つめのサーボが、デフォルトの100μsecのディレイのあと、2つめ、3つめと、350μsec以上ずつずらしたときに返答がありました。
つまり、パケットが混信しなかったということになります。
せっかくなので、一番速い350μsecを採用しました。

受信するデータは、下記の通りです。
“現在位置”から10バイト分取得します。

  • 現在位置
  • 現在時間
  • 現在スピード
  • 現在負荷
  • 現在温度

送るパケットは下記のソースの通りです。


// パケット作成
sendbuf[0] = (unsigned char)0xFA; // ヘッダー1 
sendbuf[1] = (unsigned char)0xAF; // ヘッダー2 
sendbuf[2] = (unsigned char)0xFF; // サーボID 
sendbuf[3] = (unsigned char)0x0F; // フラグ(0x0F) 指定アドレスからの指定の長さを返答 
sendbuf[4] = (unsigned char)0x2A; // アドレス(0x2A) 現在位置 
sendbuf[5] = (unsigned char)0x0A; // 長さ(10byte) 
sendbuf[6] = (unsigned char)0x00; // 個数 (任意アドレスリターンの場合はcnt=0x00)
// チェックサムの計算 
sum = sendbuf[2]; 
for (i = 3; i < 7; i++) {
 sum = (unsigned char)(sum ^ sendbuf[i]); 
} 
sendbuf[7] = sum; // チェックサム

さて、準備は整いました。

どれくらいの速度が出るのか・・・

 

じゃん!

なんと、1サイクル11msecの速度で制御出来るようになりました。

ちなみに1サイクルの処理は

  • サーボ22個分の情報取得
  • サーボ22個分のトルク情報(ON/OFF)の送信
  • サーボ22個への角度・速度の送信

と言う感じです。

つまり、20Hzが限界と思っていた制御周期が90Hzまで高速化できました!

YouTube Preview Image

20Hzの時とは比べ物にならないくらいヌルヌル動きます。
限界は勝手に決めてはダメということですね!

 

…で、そこから少し進めて、リアルタイムで、ティーチングプレイバックを行えるようにしました。

サーボの制御のスレッドとは別スレッドで、キャプチャと再生のスレッドを回すようにしたので、ある程度リアルタイム性は担保されているかと思います。

コントロールパネルにだいぶんボタンが増えてきました。

キャプチャしたデータは、とりあえず、CSV形式で保存しています。
ゆくゆくはちゃんとファイルフォーマット考えよう…。

動作するところを動画で撮影しています。

YouTube Preview Image

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

広告

Top