//---------------------------------------------------------// // // Granule Ishihama Yoshiaki All right reserved // ishmnn@cap.bekkoame.ne.jp // //---------------------------------------------------------// import java.awt.*; import java.applet.*; import java.io.*; import java.lang.String; import java.util.Random; import java.util.Date; public class Granules extends Applet implements Runnable { Thread runner; int NUM, WIDTH,HEIGHT,i,j,myPhase=0,st=0; Graphics g2; CGranule granule[]; Random nrand; public void init() { Date d=new Date(); nrand=new Random(d.getTime()); WIDTH=this.size().width; HEIGHT=this.size().height; String s; g2=this.getGraphics(); g2.setColor(Color.black); g2.fillRect(0,0,WIDTH,HEIGHT); s=getParameter("NUM"); if (s==null)NUM=50; else NUM = Integer.parseInt(s); setBackground(Color.black); setForeground(Color.white); granule=new CGranule[NUM]; for(i=0;i < NUM;i++){ granule[i]=new CGranule(); granule[i].DoInit(WIDTH,HEIGHT,nrand); } } public void start() { if (runner == null) { runner= new Thread(this); runner.start(); } } public void stop() { if (runner!=null) { runner.stop(); runner=null; } } public void run() { while (true) { try { Thread.sleep(10); } catch (InterruptedException e){}; if ( isVisible() ) { DomyRun(); offpaint(); } } } public void DomyRun()//----------------------------------// { switch(myPhase){ case 0: //------------- Normal State -----------// st ++; if(st > 400) { st=0; myPhase=10; } for(i=0;i < NUM;i++) { int total=0; double[] LOC,loc; int[] myCellP,cellp; LOC=new double[2]; loc=new double[2]; myCellP=new int[2]; cellp =new int[2]; LOC[0]=LOC[1]=0.0; granule[i].GetCellPoint(myCellP); for(j=0;j < NUM;j++){ if(j==i) continue; granule[j].GetCellPoint(cellp); if(java.lang.Math.abs(myCellP[0] - cellp[0]) < 2 && java.lang.Math.abs(myCellP[1] - cellp[1]) < 2){ granule[j].DoGetLoc(loc); LOC[0] +=loc[0]; LOC[1] +=loc[1]; total ++; } } if(total!=0){ double f1; f1= total; loc[0]=LOC[0]/f1; loc[1]=LOC[1]/f1; } else { loc[0]=loc[1]=0.0; } granule[i].SetVelocity(loc); granule[i].Course(nrand); granule[i].Mechanics(); } break; case 10: //--------- Explosion ------------// for(i=0;i < NUM;i++) granule[i].SetPhase(100); myPhase=11; break; case 11: for(i=0;i < NUM;i++){ granule[i].Course(nrand); granule[i].Mechanics(); } st ++; if(st > 170){ st=0; myPhase=0; for(i=0;i < NUM;i++) granule[i].SetPhase(110); } break; } }//-----------------------------------------------------// public void offpaint () { int k; int[] nn; nn=new int[2]; for (k=0;k < NUM;k++){ g2.setColor(Color.black); granule[k].DoGetOldLocInt(nn); g2.drawLine(nn[0],nn[1],nn[0], nn[1]); g2.setColor(Color.white); granule[k].DoGetLocInt(nn); g2.drawLine(nn[0],nn[1],nn[0], nn[1]); } } public void paint(Graphics g2) { //g2.drawImage(offscreen, 0, 0,Color.black,this); } } //------------------------------ CGranule -----------------------// public class CGranule { int phase,st,count,sx,sy; double[] loc, vct, deltaVCT,oldDelta; double maxx,minx,maxy,miny,mycenterX,mycenterY; int[] cellP,oldLoc; public int rand(Random nrand,int range) { return( java.lang.Math.abs(nrand.nextInt()) % range); } public void DoInit(int Width,int Height,Random nrand) { double f1; loc=new double[2]; vct=new double[2]; deltaVCT=new double[2]; oldDelta=new double[2]; st=0; phase=10; deltaVCT[0]=0; deltaVCT[1]=0; sx=Width; sy=Height; loc[0]=rand(nrand,sx) - sx/2; loc[1]=rand(nrand,sy) - sy/2; f1=rand(nrand,360)-180; f1 *=0.01745; vct[0]=java.lang.Math.cos(f1); vct[1]=java.lang.Math.sin(f1); maxx=sx/2; minx=-maxx; maxy=sy/2; miny=-maxy; mycenterX=maxx; mycenterY=maxy; cellP=new int[2]; oldLoc=new int[2]; oldLoc[0]=oldLoc[1]=0; SetCellPoint(); } public void Mechanics() { vct[0] += deltaVCT[0]; vct[1] += deltaVCT[1]; loc[0] +=vct[0]; loc[1] +=vct[1]; } public void DoGetLoc(double dst[]) { dst[0] = loc[0]; dst[1] = loc[1]; } public void DoGetLocInt(int dst[]) { dst[0] =(int)( loc[0] + mycenterX); dst[1] =(int)( loc[1] + mycenterY); oldLoc[0]=dst[0]; oldLoc[1]=dst[1]; } public void DoGetOldLocInt(int dst[]) { dst[0] =oldLoc[0]; dst[1] =oldLoc[1]; } public void Course(Random nrand) { switch(phase) { case 10: //-------- Normal ----------// if(CheckClosure()) return; SetCellPoint(); break; case 100: //-------- Explosion -------// {double f1; f1=rand(nrand,360)-180; f1 *=0.01745; deltaVCT[0]=java.lang.Math.cos(f1); deltaVCT[1]=java.lang.Math.sin(f1); vct[0]=0; vct[1]=0; phase=101;st=0; } break; case 101: st ++; if(st > 20){ st=0; oldDelta[0]=deltaVCT[0]; oldDelta[1]=deltaVCT[1]; deltaVCT[0]=0; deltaVCT[1]=0; phase=102; } CheckClosure2(); break; case 102: st ++; if(st > 50){ st=0; deltaVCT[0]=-oldDelta[0] * 0.2; deltaVCT[1]=-oldDelta[1] * 0.2; phase=103; } CheckClosure2(); break; case 103: CheckClosure2(); break; case 110: phase=10; CheckClosure2(); break; } } public boolean CheckClosure() { if(loc[0] > maxx) { if( vct[0] > 0 ){ vct[0]=-vct[0]; deltaVCT[0]=0; return true; } } if(loc[0] < minx){ if(vct[0] < 0 ){ vct[0]=-vct[0]; deltaVCT[0]=0; return true; } } if(loc[1] > maxy){ if(vct[1] > 0 ){ vct[1]=-vct[1]; deltaVCT[1]=0; return true; } } if(loc[1] < miny){ if(vct[1] < 0 ){ vct[1]=-vct[1]; deltaVCT[1]=0; return true; } } return false; } public void CheckClosure2() { if(loc[0] > maxx) { if( vct[0] > 0 ){ vct[0]=-vct[0]; deltaVCT[0]=-deltaVCT[0]; } } if(loc[0] < minx){ if(vct[0] < 0 ){ vct[0]=-vct[0]; deltaVCT[0]=-deltaVCT[0]; } } if(loc[1] > maxy){ if(vct[1] > 0 ){ vct[1]=-vct[1]; deltaVCT[1]=-deltaVCT[1]; } } if(loc[1] < miny){ if(vct[1] < 0 ){ vct[1]=-vct[1]; deltaVCT[1]=-deltaVCT[1]; } } } public void SetCellPoint() { int s1,s2,s3,s4; s1= (int)loc[0] + sx/2; s2= (int)loc[1] + sy/2; s3=sx/10; s4=sy/10; cellP[0]=s1/s3; cellP[1]=s2/s4; } public void GetCellPoint(int dst[]) { dst[0]=cellP[0]; dst[1]=cellP[1]; } public void GetVelocity(double dst[]) { dst[0]= vct[0]; dst[1]= vct[1]; } public void SetVelocity(double p0[]) { double px,py, fp1; px=p0[0] - loc[0]; py=p0[1] - loc[1]; fp1= myLength2d(px,py); fp1= fp1/5.0; if(fp1!=0.0) { px /=fp1; py /=fp1; } else{ px=py=0.0; } px -= vct[0]; py -= vct[1]; deltaVCT[0]=px/10.0; deltaVCT[1]=py/10.0; } public double myLength2d(double px,double py) { double f; f=px*px + py*py; f=java.lang.Math.sqrt(f); return f; } public int GetPhase() { return phase; } public void SetPhase(int s) { phase=s; } }