チュートリアル 07 autocount2 - MaxClock

このクラスは autocount1に自動的な処理を追加したものです。前のバージョンでは count を1増加させて、その結果を出力するためには、bang の入力が必要でしたが、下に示すクラスでは、MaxClock クラスを使用してクロック(clock)を生成し、ユーザがセットした時間間隔で定期的にbang メソッドが呼び出されます。

import com.cycling74.max.*;

public class autocount2 extends MaxObject implements Executable {

	private MaxClock clock;
	private int count=0;
	private float interval=400.f;
	
	public autocount2() {
		declareAttribute("count");
		declareAttribute("interval");
		clock = new MaxClock(this);
	}

	public void inlet(int i) {
		if (i==1)  
			clock.delay(0);
		else 
			clock.unset();
	}

	public void execute() {
		bang();
		clock.delay(interval);
	}

	protected void notifyDeleted() {
		clock.unset();
	}

	public void bang() {
		count++;
		outlet(0, count);
	}
}

最初に気が付くのは、autocount2 クラスが MaxObject を拡張しているだけではなく、Executable インターフェイスを実装(impliments)している点でしょう。Java のインターフェイス(Interface)は無関係なオブジェクトどうしがお互いにやりとりを行なうために使用する機構です。インターフェイスは動作を定義するために使用でき、任意のクラスで実装(impliment)することができます。クラスで Executable を実装するために必要なものは、execute() メソッドだけです。

ここでは、新しい MaxClock を作った場合、Executable の中の私たちのクラスがコンストラクタの中にあるという事実を使っています。 MaxClock クラスのコンストラクタは、アーギュメントとしてExecutable を必要とします。その後、クロックが実行されると、MaxClock は オブジェクトが生成されるときに渡された Executable オブジェクトの中のexecute メソッドを呼び出します。ここでは、キーワード this を渡していますが、これは "this object"(このオブジェクト)を短縮したものです。言い換えると、新しい autocount2 オブジェクトはMaxClock コンストラクタに対し、自分自身を Excutable として渡し、MaxClock が動作を開始すると、autocount2 オブジェクトの execute メソッドが呼び出されます。

MaxClockdelay(double) メソッドを呼び出すことにより、将来のある時点で動作するよう命じることができます。この double の値は実行前のクロックの待ち時間をミリ秒で表したものです。上のクラスの場合、 mxj オブジェクトが 1 を受け取ると、コードは clock.delay(0) を呼び出します。右インレットにtoggle が接続された場合、この動作が起きます。このとき、execute メソッドが直ちに呼び出され、このメソッドによって bang が呼び出されます。この bang は count の値を増加させ、その結果を出力します。そして、clock.delay(interval) が呼び出されますが、これによりexecute メソッドは 400 ミリ秒後に再び呼び出されます。400 がinterval という変数のデフォルトの値ですが、この変数はアトリビュートとして宣言されているため、ユーザが interval メッセージを使って新しい値に設定することができるという点に注意して下さい。

このクラスでは notifyDeleted メソッドも導入されています。推測できるかも知れませんが、このメソッドは、Max パッチの中で Java クラスを持つ mxj オブジェクトが削除された場合に呼び出されます。このメソッドの代表的な使用法は、オブジェクトが存在している間に作り出された「未解決の問題」のすべてを停止させることです。この例で、未解決なものはMaxClock の処理を行なうことだけです。 MaxClock は実行時にはオブジェクトのexecute メソッドを何回も呼び出し続けます。bang メソッドが必要とするアウトレットが存在しなくなってしまったとしたら、惨憺たる結果になってしまうでしょう。clock.unset の呼び出しによって、MaxClock が予定していた将来にわたる execute の呼び出しは停止されます。

実行例: