メッセージGetのプログラミング作法の解析が完了しましたので、このパターンをまねして新しいメッセージを作成していきましょう。
すでに述べましたが、新規にメッセージを作る際には“最初にそのメッセージのクラスを作る”必要があります。
MSRS内に、すでにいくつかのメッセージ(例えば、Replace、Updateなど……)が定義されているので、今回はMSRSの「Replace」を使って新たにメッセージを作成することにします。ちなみに、Replaceとはサービスの状態を変更するメッセージです。
Replaceはサービスに対して働き掛けるメッセージなので、“状態”が必要になります。まず、MyProj2Types.csファイルに対して、ソース5のように状態を定義します。
ここでは状態のプロパティとして、
を定義します。
ソース6のようにポートセットに対して、新規にReplaceを追記します。
これで、MyProj2Operationsというポートセットに対して、Replaceというメッセージが投函可能になりました。
ポートセットMyProj2Operationsに対して投函するReplaceメッセージのクラスをソース7のように定義します。
ソース7を見てお分かりのとおり、MSRSのReplaceをそのまま継承しています。
ポートセットのインスタンスの生成は、テンプレートに手を入れる必要はありません。
Replaceのハンドラは、ソース8のように記述します。
属性の部分は、
[ServiceHandler(ServiceHandlerBehavior.Exclusive)]
とします。
ここで、ServiceHandlerBehaviorはExclusiveとします。ここはとても重要なポイントです。ソース4のGetのハンドラを見てください。Getの属性において、ServiceHandlerBehaviorはConcurrentとなっています。Getは、サービスの状態を読み出すメッセージです(一般に、データを読み出す処理は複数のプログラムを同時並行的に実行することができます)。
ところが、Replaceはサービスの状態を書き換える処理です。例えば、2つ以上のプログラムが、同時にデータを書き換える処理を行うと、結果がどのようになるか予想できません。このような処理をクリティカル セクション(critical section)といいます。
このような問題を回避する手段として、ServiceHandlerBehaviorをExclusiveとしています。このようにすることで、このハンドラが処理を行っている間、ほかのプログラムはこのデータにアクセスできなくなります。つまり、排他制御が行われるのです。
Replaceの処理はGetとは異なり、
_state = replace.Body;
によってメッセージの中身を状態へセットして、
replace.ResponsePort.Post(DefaultReplaceResponseType.Instance);
により処理の終了をポストします。
プログラムの作成は以上で終了です。それでは、MyProj2をビルドしてください。
ビルドが無事に成功したら、VPLを起動します。
[Basic Activities]のツールボックスから、画面1のように、3つの[Data]をドラッグし、状態のプロパティに合わせてデータを設定します。
次に、[Basic Activities]のツールボックスから、画面2のように[Join]をドラッグし、[Data]と接続します。
[Join]の入力ポートは2口なので、3つ目の[Data]が接続できないように思えます。しかし、3つ目の[Data]から強引に[Join]へ線を引っ張ると、画面3のように入力ポートが3口に拡張され、3つのメッセージをまとめる[Join]が作成できます。
続いて、[Services]のツールボックスから[MyProj2]をドラッグして、[Join]と接続します。
画面4のように、[Connections]ダイアログが開くので、[To]ペインで[Replace]を選択します。
続いて、[Data Connections]ダイアログが開くので、画面5のように入力とプロパティの関連付けを行います。
これで、MyProj2の状態は変更されました。
変更をチェックするためにもう1つ[MyProj2]をドラッグして、2つの[MyProj2]を接続します。すると、画面6のように[Connections]ダイアログが開くので、[From]ペインで[Replace - Success]を選択し、[To]ペインで[Get]を選択します。設定が完了したら[OK]ボタンをクリックします。
最後に、画面7のように3つのダイアログをドラッグして、[MyProj2]と接続します。
このときに、[Connections]と[Data Connections]ダイアログにおいても、連載第3回「サービスはロボットの状態と連動して動くもの」を参考にして、正しい設定を行ってください(注)。
以上でダイヤグラムは完成です。
これを実行してみると意図したとおり、3つのダイアログが開くはずです(画面8)。
「ポート」と「ハンドラ」の解説は以上です。それでは、最後に今回の内容の理解度をチェックしてみましょう。以下に演習問題を2つ用意しました。ぜひチャレンジしてください。(次回に続く)
演習問題1:
今回、MyProj2でメッセージの名前を「Replace」としましたが、メッセージの名前を「SetState」としてプログラムを作ってください。
演習問題2:
メッセージの名前「Replace」を「SetVelocity」に変更して、状態のプロパティの「rotVelocity」だけを変更するプログラムを作ってください。ちなみに、ほかのプロパティは変更してはいけません。
Copyright © ITmedia, Inc. All Rights Reserved.