TestApplet2の実行ページ

波紋が広がる簡単なアプレット

アプレットプログラムのレポートツールでの作成方法はreportのページを参照。

javaコンソールを開くと下記の プログラムのSystem.out.printlnの書き出しを見ることができ
IE等のブラウザーの操作でどのようなメソッが呼ばれるか確認できる。
javaコンソールの開き方

  1. ページを表示するとinitが呼ばれインスタンスを初期化、続いてstartが呼ばれ動き始める。
  2. ページを移動するとstopが呼ばれ、続いてdestroyが呼ばれインスタンスが破棄される。

ソースコード:TestApplet2.java
   HTMLのソースコード:TestApplet2.html


TestApplet2.jar jarで実行できるように若干改変しています

import java.applet.Applet;
import java.awt.*;

public class TestApplet2 extends Applet implements Runnable
{
	Wave waveList[]=null;

	//次の2変数は複数のスレッドから同時に参照される可能性があるのでvolatile修飾子を付けた
	//volatile修飾子:
	// 複数のスレッドから参照されるので、変数の一時コピーを作るなどの最適化を抑制する
	volatile Thread thread=null;//別スレッドの実行フラグとして使う
	volatile boolean paintOK=false;//描画準備完了か?
	//
	public TestApplet2()
	{
		System.out.println("コンストラクタTestApplet2()");System.out.flush();//フラッシュ必要
	}
	public void init()
	{
		System.out.println("init()");System.out.flush();
		initWave();
	}
	public void destroy()
	{
		System.out.println("destroy()");System.out.flush();
		//上書きする必要はない
	} 
	void initWave()//描画のための準備を行う初期化
	{
		System.out.println("initWave()");System.out.flush();
		//描画画面の用意ができるのをまつ。
		Dimension dim=null;//画面の大きさ
		//画面の大きさが決まるまでループして待つ
		while(dim==null){
			dim=getSize();
			try{
				Thread.sleep(30);//0.03秒休む
			}catch(Exception e){/*例外でも何もしない*/}
		}
		//画面の設定と波紋の準備
		setBackground(Color.white);//背景は白に
		dim=getSize();
		waveList=new Wave[(dim.width*dim.height)/5000];
		for(int i=0;i<waveList.length;i++)
			waveList[i]=new Wave(dim.width,dim.height);//各Waveを生成
		//描画準備完了のフラグを立てる
		paintOK=true;
	}

	//start、stopでThreadを制御
	public void start()
	{
		System.out.println("start()");System.out.flush();
		if(thread==null){
			thread=new Thread(this);
			thread.start();
		}

	}
	public void stop()
	{
		System.out.println("stop()");System.out.flush();
		thread=null;
	}
	public void run()
	{ 
		System.out.println("run()");System.out.flush();
		//実行中の無限ループ
		while(thread!=null){
			for(int i=0;i<waveList.length;i++)
				waveList[i].next();//各Waveを更新
			repaint();//再描画
			try{
				Thread.sleep(30);//0.03秒休む
			}catch(Exception e){/*例外でも何もしない*/}
		}
	}

	//描画関連
	public void paint(Graphics g)
	{
		if(paintOK){//画面が用意できていれば描画
			for(int i=0;i<waveList.length;i++)
				waveList[i].paint(g);//各Waveを描画 
		}else{
			//時間が短いので、おそらく見ることは無いだろうが用心して書いておく
			g.drawString("準備中ですしばらくお待ちください",10,20);
		}
	}
}

/*波紋のクラス*/
class Wave
{
	//波の色を予め準備
	static final int RMAX=64;
	static Color clist[]=null;
	static{
		clist=new Color[RMAX+1];
		double k=240.0/RMAX;
		int t;
		for(int i=0;i<=RMAX;i++){
			t=(int)(i*k);
			clist[i]=new Color(t,t,240);
		}

	}

	//インスタンスのメンバ
	int width=100,
	height=100,
	x=0,//波の中心のx座標
	y=0,//波の中心のy座標
	r=0;//波の半径
	Wave(int w,int h)
	{
		width=w; height=h;
		x=(int)(Math.random()*width);
		y=(int)(Math.random()*height);
		r=0;
	}

	void next()
	{
		if(r==0){
			if(0.995<Math.random())r=1;
		}else if(r==RMAX){
			x=(int)(Math.random()*width);
			y=(int)(Math.random()*height);
			r=0;
		}else r++;
	}

	void paint(Graphics g)
	{
		if(r==0)return;
		g.setColor(clist[r]);
		g.drawOval(x-2*r,y-2*r,4*r,4*r);
	}

}