「AX-S1で最大音量を測定し、それに対応した角度へAX-12+のホーンを動かす」というプログラムを作成します。
GCC Developer Liteを起動して、Chapter3で作成したプログラムを開いて下さい。
メニューの「ファイル」→「開く」→ ファイル(AutomaticDoor.c)を選択し、「開く」をクリックします。
ファイルを別の名前で保存します。
メニューの「ファイル」→「名前を付けて保存」→ファイル名に「SoundMeter.c」と入力し、Chapter1.3のサンプルプログラムのダウンロード[4]で作成したSampleフォルダに「保存」します。
今回のプログラムでは条件による分岐がありませんので、以下のif~else~文を削除します。
if (ReadData > 100) { fd_DXWriteWordData (1, 30, 300); fd_Wait (2000); } else { fd_DXWriteWordData (1, 30, 512); }
Chapter3ではAX-S1の正面赤外線反射センサの値を取得しました。今回は最大音量を取得します。
AX-S1コントロールテーブル[7]を見て下さい。音量最大保持値はアドレス36です。 音量最大保持値はアドレス35の音量測定値の最大値を保持し続けます。
fd_DXReadByteData (100, 27, &ReadData);
の第2引数を36に書き換えます。
fd_DXReadByteData (100, 36, &ReadData);
AX-12+のホーンの角度をメーターに見立て、音量最大保持値に対応した角度にホーンを動かします。
AX-12+のホーンを動かすには、AX-12+のコントロールテーブルのアドレス30,31にゴールポジションを書き込みます。2バイトのデータを書き込むにはfd_DXWriteWordData関数を使います。詳しくはChapter3.3のバーを開ける[9]を参照して下さい。
fd_DXWriteWordData (1, 30, ゴールポジション);
ゴールポジションの部分には何を入れれば良いでしょう?
音量最大保持値に対応した角度にAX-12+のホーンを動かしますので、ゴールポジション=音量最大保持値です。
音量最大保持値は
fd_DXReadByteData (100, 36, &ReadData);
で変数ReadDataに代入されます。従ってゴールポジションにはReadDataと書きます。
fd_printf ("%3d\r", ReadData); の後ろに
fd_DXWriteWordData (1, 30, ReadData);
と入力します。 ReadDataの前に&は付けません。変数の前に&を付けるとその変数のアドレス[10]になります。 ゴールポジションに書き込むのは、ReadDataのアドレスではなく、ReadDataに入っている値です。
ゴールポジションのデータの範囲は0~1023でした。 音量最大保持値のデータ範囲はどうでしょう。
音量センサの値はChapter2.5の課題[12]で紹介した通り、128を中心に音がすると音量に応じて上下に揺れます。 音量最大保持値は音量センサの最大値を保持した値なので、音量最大保持値の範囲は128~255となります。
ゴールポジションはせっかく0~1023の範囲があるので、音量最大保持値を3倍した値を代入することで、コールポジションの範囲を384~765にします。
つまり音量最大保持値が128のときゴールポジションは384、200のとき600、255のとき765になります。
fd_DXWriteWordData (1, 30, ReadData * 3);
上記のように書き換えます。*は掛け算です。
音量最大保持値は、音量の最大値を保持し続けます。従って一度値が最大の255になると、それ以降は255から変化することはありません。もう一度初めから測定するために音量最大保持値をプッシュボタンでリセットするようにします。
以下はFDIII-HCのプッシュボタンの状態を取得する関数です。
bool fd_GetPB (void);
戻り値はプッシュボタンの状態です。ボタンが押されているとtrueを返し、押されていないとfalseを返します。 引数はありません。
uint8_t ReadData;の後ろに
bool PB;
と入力します。 プッシュボタンの状態を保存するための変数です。 boolは、true又はfalseで表されるデータの型です。
fd_DXWriteWordData (1, 30, ReadData * 3); の後ろに
PB = fd_GetPB();
と入力します。変数PBにプッシュボタンの状態が代入されます(true:押されている、false:押されていない)。
プッシュボタンが押されたら音量最大保持値をリセットします。前項より「プッシュボタンが押されたら」は、もし変数PBがtrueならと言い代えられます。 もし~なら~という条件分岐には、if分を使います。
PB = fd_GetPB();の後ろに
if(PB == true){ }
と入力します。PB=trueではなくPB==trueです。「=」だとPBにtrueが代入されてしまうだけで、ifの条件にはなりません。 変数PBがtrueなら、つまりプッシュボタンが押されたらifの後の{ }内を実行します。
fd_DXWriteByteData関数でAX-S1の音量最大保持値(アドレス36)に0を書き込みます。 if(PB == true){の後に
fd_DXWriteByteData (100, 36, 0);
と入力します。 第1引数のIDは100、第2引数のアドレスは36、第3引数の書き込む値は0です。
#include <fd.h> #define KEY_QUIT { if(fd_rx_buff()) fd_SoftReset();} void main (void) { uint8_t ReadData; bool PB; fd_Init (0, BT_CONSOLE, FD_BEEP_MMI | FD_BEEP_PACKETERR | FD_BEEP_LOWVOLTAGE | FD_BEEP_BOOTUP, 7.4); fd_DXWriteWordData (1, 34, 200); while (1) { fd_DXReadByteData (100, 36, &ReadData); fd_printf ("%3d\r", ReadData); fd_DXWriteWordData (1, 30, ReadData * 3); PB = fd_GetPB(); if(PB == true){ fd_DXWriteByteData (100, 36, 0); } KEY_QUIT; } }
プログラムが完成しました。プログラムを書き込んで動かしてみましょう。
FDIII-HCのプッシュボタンを押しリセットしてから、音を出すとAX-12+が音量に応じて動くことを確認しましょう。
(This host) = https://www.besttechnology.co.jp