次に、SCADA情報として入力した模擬計測値が、あらかじめ設定した値を超えたら警報を発するようにしてみます。
まず、Javaで記述した模擬依頼者プログラムにコードを追加し、警報音の鳴動開始と、同停止手続きを追加します。
警報音のファイルは、構築子を定義してその中で読み込むようにしたかったのですが、構築子を定義すると、なぜかJavaFXのプログラムからJavaプログラムの手続きを呼び出さなくなってしまいます(誤りが発生するわけでもありません)。仕方ないので、実体変数の定義時に初期化を行って、音声ファイルを読み込むようにしました。
私は、警報音ファイルとして、自分のPCにあった「ALERT.WAV」を使用しました。Javaのプログラムでの音声ファイルの扱いについては、この投稿を参照してください(今回、警報文は、JavaFXのプログラムで表示することにしました。また、鳴動開始と停止を別の手続きにしています)。
音声ファイルを「企画名\build\classes\包み名」ディレクトリに置きます。そして、NetBeansの「プロジェクト」窓でJavaファイルをマウスで右押しし、「ファイルをコンパイル」を選択実行して、Javaファイルを一括変換しておきます。
最後に、Javaプログラムのコードを載せておきます。
package client;
import java.applet.Applet;
import java.applet.AudioClip;
public class ScadaClient {
private AudioClip ac = Applet.newAudioClip(ScadaClient.class.getResource("ALERT.WAV"));
// 模擬SCADAデータ生成用作業変数。
private int i = -1;
public double receiveData() {
// 模擬SCADAデータを生成して返す。
i += 1;
if (i >= 360) {
i = 0;
}
return (double)(Math.abs(Math.sin(i * Math.PI / 180.0) * 100));
}
public void startAlarm() {
ac.loop();
}
public void stopAlarm() {
ac.stop();
}
public static void main(String[] args) {
ScadaClient sc = new ScadaClient();
for (int i = 0; i < 5; i++) {
System.out.println(sc.receiveData());
}
}
}
2 件のコメント:
> 構築子を定義すると、なぜかJavaFXのプログラムからJavaプログラムの手続きを呼び出さなくなってしまいます
この部分の詳細を教えていただけないでしょうか?
気になるので、ちょっと調べてみようと思います。
最初は、ScadaClientクラスに実体変数「private AudioClip ac;」の宣言と、引数なしの構築子の定義「ScadaClient() {}」を追加し、構築子の中で、「ac = Applet.newAudioClip(ScadaClient.class.getResource("ALERT.WAV"));」を実行して、音声ファイルを読み込むようにしました。
しかし、こうすると、それまでJavaFXのプログラムから呼び出すことによって、実数値を更新しながら返していた「receiveData() 」手続きが、毎回0.0を返すようになってしまいました(と言うより、実際には手続き自体を呼び出していないのではと思っています)。
このとき、誤りは何も発生しません。
また、音声ファイルの鳴動開始、停止続き「startAlarm()」 、「stopAlarm()」も呼び出されません(同様に誤りは発生しません)。
JavaFXのプログラムで、ScadaClientクラスの実体を生成しているのですが(2007年12月19日の投稿をご覧ください)、これが何か関係しているのではないかと個人的には思っているのですが、突き詰めていません。m(_ _;)m
何かお分かりになりましたら、コメントいただけるとうれしいのですが。
コメントを投稿