1: 2011-07-11 (月) 14:05:38 yoshida ソース 現: 2013-04-09 (火) 23:52:52 takaboo ソース
Line 5: Line 5:
SIMPLE TERMからのキー入力によって、カメラを動かす方向を変えます。 SIMPLE TERMからのキー入力によって、カメラを動かす方向を変えます。
-キーボードのテンキーを使って6なら右、4なら左、8なら上、2なら下へ動き、0でブートローダへ移行します。+キーボードの方向キー、又はテンキーの'8'、'2'、'4'、'6'を使って上下左右に動き、[ESC]キーでプログラムを終了します。
-#ref("camera_block.png")+#ref(flow.png)
-**準備 [#m41943fd]+**初期化 [#m41943fd]
-GCC Developer Liteを起動します。以下基本的な部分を入力します。+GCC Developer Liteを起動し、初期化部分を記述します。 
 +#html{{ 
 +<pre class="brush:c"> 
 +  fd_SetBeepCondition (FD_BEEP_MMI | FD_BEEP_PACKETERR | FD_BEEP_LOWVOLTAGE | FD_BEEP_BOOTUP); 
 +  fd_SetUVThreshold (7.4); 
 +  DX_ChangeBaudrate (1000000); 
 +</pre> 
 +}}
- #include <fd.h>+**キーボード入力関数の作成 [#y215f66b]
-&nbsp;void main (void) { +通常のキー入力では1回の押下で1バイトが入力されます。方向キーの場合は、1回の入力で3バイトも入力されます。~ 
-   fd_Init (0, BT_CONSOLE, FD_BEEP_MMI | FD_BEEP_PACKETERR | FD_BEEP_LOWVOLTAGE | FD_BEEP_BOOTUP, 7.4); +機種により値が異なる可能性がありますので、ご注意ください。 
- }+| 1バイト目 | 2バイト目 | 3バイト目 | 方向キー | 
 +| 0x1b      | 0x5b      | 0x41      | 上キー | 
 +|^          |^          | 0x42      | 下キー | 
 +|^          |^          | 0x43      | 右キー | 
 +|^          |^          | 0x44      | 左キー | 
 +方向キーをテンキーの数字に合わせます。 
 +| 方向キー | 上キー | 下キー | 右キー | 左キー | 
 +| テンキー | '8' | '2' | '6' | '4' | 
 +テンキーはキーボードの右側に位置している数字キー等のことです。~ 
 +#html{{ 
 +&lt;pre class="brush:c"> 
 +// キーボード入力関数 
 +int getCrossKey () { 
 + ; int result = -1// 戻り値 
 +  int cnt = 0;      // ループ用カウンタ 
 +  int rcv = 0;      // 入力文字バッファ 
 +  while (fd_rx_buff () && cnt < 3) {          // 入力バイトが残っており、3バイト目の処理が終了するまで繰り返す 
 +   rcv = fd_getc ();                        // 1バイト入力 
 +   switch (cnt) { 
 +     case 0: if (rcv == 0x1b) cnt++; break;  // 1バイト目が0x1bか確認 
 +     case 1: if (rcv == 0x5b) cnt++; break;  // 2バイト目が0x5bか確認 
 +     default: 
 +       switch (rcv) {                        // 十字キー以外は読み飛ばし 
 +         case 0x41: result = '8'; break;    // 上キー 
 +         case 0x42: result = '2'; break;    // 下キー 
 +         case 0x43: result = '6'; break;    // 右キー 
 +         case 0x44: result = '4'; break;    // 左キー 
 +       } 
 +       cnt++; 
 +       break; 
 +   } 
 +  } 
 +  if (cnt != 3) result = rcv; // 通常のキーボード入力 
 +  return result; 
 +
 +</pre> 
 +}}
- #define KEY_QUIT { if(fd_rx_buff()) fd_SoftReset();} +**変数 [#nfde1082
-は、何かキー入力があったらブートローダに戻るという記述ですが、今回はキー入力を使うのでKEY_QUITは使えません。 +パン(横振り)・チルト(上下振り)のポジション用に使う変数PanPositionとTiltPositionをuint16_t型で用意します。AX-12Aのホーンが真ん中になるよう、初期値を512とします。~ 
-キー入力が0ならfd_SoftReset関数を実行するようにします。 +入力バッファ用の変数inkeyと、ESCキー入力時の処理の終了判断を行うためのiendをint型で宣言します。 
- +#html{{ 
-**変数の用意 [#y215f66b+&lt;pre class="brush:c"> 
- +  int inkey, iend = 0
-入力された文字を取得する変数cと、パン(横振り)・チルト(上下振り)のポジション用に使う変数PanPositionとTiltPositionを用意します。 +  uint16_t PanPosition = 512, TiltPosition = 512; 
- +</pre> 
-&nbsp;char c; +}}
- uint16_t PanPosition = 512, TiltPosition = 512; +
- +
-AX-12+のホーンが丁度真ん中になる512に初期化します。+
**トルクリミット [#b23b37f8] **トルクリミット [#b23b37f8]
-ID=1と2のAX-12+のトルクリミット(アドレス34,35)を400にします。+ID=1と2のトルクリミットを154にします。
-fd_Initの後に以下を入力します。+#html{{ 
 +<pre class="brush:c"> 
 +  fd_DXSetTorqueLimit (1, 154); // ID1のトルクリミットに154を設定 
 +  fd_DXSetTorqueLimit (2, 154); // ID2のトルクリミットに154を設定 
 +</pre> 
 +}}
- fd_DXWriteWordData (1, 34, 400); +トルクが不足している場合は適宜増加します。
- fd_DXWriteWordData (2, 34, 400);+
-**初期ポジションへ移動 [#vfd65e43]+**初期ポジションへ移動 [#n7949229] 
 +トルクリミット設定後、ID1とID2のゴールポジションを変更します。
-AX-12+のホーンを最初のポジションへ移動します。ゴールポジションはアドレス30,31です。 +#html{
- +&lt;pre class="brush:c"&gt
-トルクリミットの設定の後に以下を入力します。 +  fd_DXSetPosition (1, PanPosition);   // パン位置の設定 
- +  fd_DXSetPosition (2, TiltPosition);   // チルト位置の設定 
-  fd_DXWriteWordData (1, 30, PanPosition); +&lt;/pre&gt
-  fd_DXWriteWordData (2, 30, TiltPosition); +}}
- +
-**文字入力を取得する [#a6155ad4] +
- +
-文字入力を一文字取得します。 +
- +
-初期ポジションへの移動の後に以下を入力します。 +
- +
- while (1) +
-&nbsp; if (fd_rx_buff() > 0) c = fd_getc (); +
- } +
- +
-fd_rx_buffは、入力された文字数を返す関数です。fd_getcは入力された文字を1文字取得する関数です。 +
-つまり、「もし入力された文字数が0より大きければ(文字が入力されたら)、1文字取得して変数cに代入する」となります。 +
- +
-** switch文 [#r4473797] +
-取得した文字によって条件を分岐するために[[switch文>http://www.besttechnology.co.jp/modules/knowl​edge/?FDIII-HC%20Starter%20Kit%20Guide%2​0Chapter1.4#x577fb19]]を使用します。 +
-キーボードのテンキーを使って上下左右にカメラを動かします。 +
- +
-while文内の文字取得の後に以下を入力します。 +
- +
- switch (c) { +
-&nbsp;  case '6' : +
-     // 右へ +
-     break; +
-   case '4' : +
-     // 左へ +
-     break; +
-   case '8' : +
-     // 上へ +
-     break; +
-   case '2' : +
-     // 下へ +
-     break; +
-   case '0' : +
-     // ブートローダへ +
-     break; +
- } +
- +
-キーボードで6を入力すると右へ、4で左へ、8で上へ、2で下へ動くように、0でブートローダへ移行するようにプログラミングします。 +
- +
-**パン [#k17bc189] +
- +
-もし6が入力されたらPanPositionを1マイナスし、ポジションを送信します。~ +
-もし4が入力されたらPanPositionを1プラスし、ポジションを送信します。 +
- +
-switch文内のcase '6'とcase '4'に以下を入力します。 +
- +
- case '6' : +
-   PanPosition --+
-  fd_DXWriteWordData (1, 30, PanPosition); +
-  break; +
- case '4' : +
-   PanPosition ++; +
-   fd_DXWriteWordData (1, 30, PanPosition); +
-   break; +
- +
- +
- +
-取り付け方によってはプラスマイナスが逆になるかもしれません。 +
- +
-**チルト [#db024f9a] +
- +
-もし8が入力されたらTiltPositionを1マイナスし、ポジションを送信します。~ +
-もし2が入力されたらTiltPositionを1プラスし、ポジションを送信します。 +
- +
-switch文内のcase '8'とcase '2'に以下を入力します。 +
- +
- case '8' : +
-   TiltPosition --; +
-   fd_DXWriteWordData (2, 30, TiltPosition); +
-&nbsp; break; +
-&nbsp;case '2' : +
-   TiltPosition ++; +
-   fd_DXWriteWordData (2, 30, TiltPosition); +
-   break; +
- +
-取り付け方によってはプラスマイナスが逆になるかもしれません。 +
- +
-**ブートローダへ移行 [#a7bbd317] +
- +
-ブートローダへ移行する関数はfd_SoftResetです。 +
- +
-switch文中のcase '0'にfd_SoftReset関数を入力します。 +
- +
- case '0' : +
-   fd_SoftReset(); +
-   break;+
**ポジションリミット [#i21b9509] **ポジションリミット [#i21b9509]
-フレームが干渉してしまうようなポジションを送信すると、AX-12+に過大な負荷がかかり、破損する場合があります。そのようなポジションを送信しないよう、ポジションにリミッターを設けます。+フレームが干渉してしまうようなポジションを送信すると、AX-12Aに過大な負荷がかかり、破損する場合があります。そのようなポジションを送信しないよう、ポジションに仮のリミッタを設けます。
-各caseに対し以下のように追記します。+| 条件 | 移動方向 | リミッタ | 
 +|右へ移動 | パン位置減算 | パン位置 > 0 | 
 +|左へ移動 | パン位置加算 | パン位置 < 1023 | 
 +|上へ移動 | チルト位置減算 | チルト位置 > 200 | 
 +|下へ移動 | チルト位置加算 | チルト位置 < 800 |
-     case '6' : +取り付け方によっては、移動方向やリミッタの数値が異なります。フレームが干渉しないように十分確認して下さい。
-       PanPosition --; +
-       if (PanPosition < 0) PanPosition = 0; +
-       fd_DXWriteWordData (1, 30, PanPosition); +
-       break;+
-PanPositionが0より小さいなら、PanPositionを0にします。+**メインループ [#vfd65e43]
-&nbsp;     case '4' : +プッシュボタンが押されるか、ESCが押されると終了(ここでは終了フラグを参照)するwhile文を作成します。 
-&nbsp;      PanPosition +++#html{{ 
-        if (PanPosition &gt; 1023) PanPosition = 1023; +&lt;pre class="brush:c"&gt
-&nbsp;       fd_DXWriteWordData (1, 30, PanPosition)+  while (!fd_GetPB () && !iend) { 
-       break;+&lt;/pre>
 +}}
-PanPositionが1023より大きいなら、PanPositionを1023にします。+キー入力の有無を[[fd_rx_buff>FDIIILIB#c1552bcf]]関数で確認し、キー入力があれば作成したキーボード入力関数を呼出します。 
 +#html{{ 
 +<pre class="brush:c"> 
 +if (fd_rx_buff ()) { 
 +  inkey = getCrossKey (); 
 +</pre> 
 +}} 
 +方向キーはテンキーに置き換えられていますので、テンキーの数字でパン位置とチルト位置を変更します。ESCキーが入力されていれば、終了フラグをセットします。 
 +#html{{ 
 +<pre class="brush:c"> 
 +switch (inkey) { 
 +  case '6':  // 右へ移動 
 +   if (PanPosition > 0) PanPosition--; 
 +   break; 
 +  case '4':  // 左へ移動 
 +   if (PanPosition < 1023) PanPosition++; 
 +   break; 
 +  case '8':  // 上へ移動 
 +   if (TiltPosition > 200) TiltPosition--; 
 +   break; 
 +  case '2':  // 下へ移動 
 +   if (TiltPosition < 800) TiltPosition++; 
 +   break; 
 +  case 0x1b:  // 終了 
 +   iend = 1; 
 +   break; 
 +
 +</pre> 
 +}} 
 +パン位置とチルト位置を設定した後、現在の座標を表示します。 
 +#html{{ 
 +<pre class="brush:c"> 
 +fd_DXSetPosition (1, PanPosition); 
 +fd_DXSetPosition (2, TiltPosition); 
 +fd_printf ("Pan:%5d Tilt:%5d\r", PanPosition, TiltPosition); 
 +</pre> 
 +}}
-     case '8' : +**プログラム完成 [#d361e94a]
-       TiltPosition --; +
-       if (TiltPosition < 200) TiltPosition = 200; +
-       fd_DXWriteWordData (2, 30, TiltPosition); +
-       break;+
-TiltPositionが200より小さいなら、TiltPositionを200にします。 +以上で完成です。まず、名前を付けて保存します。名前はCameraPlatform.cとします。保存後、ビルドして実行してみましょう。 
-取り付け方によっては、数値が異なります。フレームが干渉しないように十分確認して下さい。 +#html{{ 
- +<pre class="brush:c"> 
-     case '2' +#include <fd.h> 
-        TiltPosition ++; +// キーボード入力関数 
-       if (TiltPosition &gt; 800) TiltPosition = 800+int getCrossKey () { 
-        fd_DXWriteWordData (2, 30, TiltPosition);+  int result = -1;  // 戻り値 
 +  int cnt = 0;      // ループ用カウンタ 
 +  int rcv = 0;      // 入力文字バッファ 
 +  while (fd_rx_buff () && cnt < 3) { 
 +   rcv = fd_getc (); 
 +   switch (cnt) { 
 +     case 0: if (rcv == 0x1b) cnt++; break;  // 1バイト目が0x1bか確認 
 +      case 1: if (rcv == 0x5b) cnt++; break;  // 2バイト目が0x5bか確認 
 +     default: 
 +       switch (rcv) {                        // 十字キー以外は読み飛ばし 
 +&nbsp;         case 0x41: result = '8'; break;    // 上キー 
 +          case 0x42: result = '2'; break;    // 下キー 
 +         case 0x43: result = '6'; break;    // 右キー 
 +         case 0x44: result = '4'; break;    // 左キー 
 +       } 
 +       cnt++;
       break;        break;
 +   }
 +  }
 +  if (cnt != 3) result = rcv; // 通常のキーボード入力
 +  return result;
 +}
-TiltPositionが800より大きいなら、TiltPositionを800にします。 +void main (void) { 
-取り付け方によっては、数値が異なります。フレームが干渉しないように十分確認して下さい。 +  int inkey, iend = 0
- +  uint16_t PanPosition = 512, TiltPosition = 512;
-**値の表示 [#a7519300] +
-PanPositionとTiltPositionの値を表示します。 +
- +
-while文内に以下を入力します。 +
- +
- fd_printf("Pan:%5d Tilt:%5d\r", PanPosition, TiltPosition); +
- +
-ここでプログラムを実行してみましょう。 +
- +
-**uint16_tの範囲 [#z2df0429] +
- +
-6を入力すると、PanPositionがだんだん減って0になり、その後65535という大きな数字になってしまいます。 +
-これは変数の型がuint16_tだからです。uint16_tはC言語でいうところのunsigned shortと同じで、値の範囲は0~65535です。そのため0から1マイナスすると65535になるのです。 +
- +
-以下のように、if文の条件を「PanPositionが60000より大きければ」に変えてみましょう。 +
- +
- case '6' : +
-   PanPosition --; +
-   if (PanPosition > 60000) PanPosition = 0; +
-   fd_DXWriteWordData (1, 30, PanPosition); +
-   break; +
- +
-**プログラム完成 [#d361e94a] +
- +
-以上で完成です。実行してみましょう。 +
- +
- #include <fd.h> +
- +
- void main (void) { +
-  char c+
-  uint16_t PanPosition = 512, TiltPosition = 512+
- +
-   fd_Init (0, BT_CONSOLE, FD_BEEP_MMI | FD_BEEP_PACKETERR | FD_BEEP_LOWVOLTAGE | FD_BEEP_BOOTUP, 7.4); +
-   fd_DXWriteWordData (1, 34, 400); +
-   fd_DXWriteWordData (2, 34, 400); +
-   fd_DXWriteWordData (1, 30, PanPosition); +
-   fd_DXWriteWordData (2, 30, TiltPosition);+
-  while (1) { +  fd_SetBeepCondition (FD_BEEP_MMI | FD_BEEP_PACKETERR | FD_BEEP_LOWVOLTAGE | FD_BEEP_BOOTUP); 
-     if (fd_rx_buff () > 0) c = fd_getc (); +  fd_SetUVThreshold (7.4); 
-    switch (c) { +  DX_ChangeBaudrate (1000000);
-       case '6' : +
-         PanPosition --; +
-         if (PanPosition > 60000) PanPosition = 0; +
-         fd_DXWriteWordData (1, 30, PanPosition); +
-         break; +
-       case '4' : +
-         PanPosition ++; +
-         if (PanPosition > 1023) PanPosition = 1023+
-        fd_DXWriteWordData (1, 30, PanPosition); +
-         break; +
-       case '8' : +
-         TiltPosition --; +
-         if (TiltPosition < 200) TiltPosition = 200; +
-         fd_DXWriteWordData (2, 30, TiltPosition); +
-         break; +
-       case '2' : +
-         TiltPosition ++; +
-         if (TiltPosition > 800) TiltPosition = 800; +
-         fd_DXWriteWordData (2, 30, TiltPosition); +
-         break; +
-       case '0' : +
-         fd_SoftReset (); +
-         break; +
-     } +
-     fd_printf ("Pan:%5d Tilt:%5d\r", PanPosition, TiltPosition); +
-   } +
- }+
 +  fd_DXSetTorqueLimit (1, 154); // ID1のトルクリミットに154を設定
 +  fd_DXSetTorqueLimit (2, 154); // ID2のトルクリミットに154を設定
 +  fd_DXSetPosition (1, PanPosition);    // パン位置の設定
 +  fd_DXSetPosition (2, TiltPosition);  // チルト位置の設定
 + 
 +  while (!fd_GetPB () && !iend) {
 +   if (fd_rx_buff ()) {
 +     inkey = getCrossKey ();
 +     switch (inkey) {
 +       case '6':  // 右へ移動
 +         if (PanPosition > 0) PanPosition--;
 +         break;
 +       case '4':  // 左へ移動
 +         if (PanPosition < 1023) PanPosition++;
 +         break;
 +       case '8':  // 上へ移動
 +         if (TiltPosition > 200) TiltPosition--;
 +         break;
 +       case '2':  // 下へ移動
 +         if (TiltPosition < 800) TiltPosition++;
 +         break;
 +       case 0x1b:  // 終了
 +         iend = 1;
 +         break;
 +     }
 +     fd_DXSetPosition (1, PanPosition);
 +     fd_DXSetPosition (2, TiltPosition);
 +     fd_printf ("Pan:%5d Tilt:%5d\r", PanPosition, TiltPosition);
 +   }
 +   fd_Wait (10);
 +  }
 +}
 +</pre>
 +}}
[[次のチャプターへ>FDIIICHAPTER7.4]]~ [[次のチャプターへ>FDIIICHAPTER7.4]]~
[[FDIII-HC Starter Kit Guide>LEARNINGGUIDE]]に戻る [[FDIII-HC Starter Kit Guide>LEARNINGGUIDE]]に戻る


トップ   差分 リロード印刷に適した表示   全ページ一覧 単語検索 最新ページの一覧   最新ページのRSS 1.0 最新ページのRSS 2.0 最新ページのRSS Atom