// ===========================================================================//	chaos2DApp.java	1996 Yushin Hozumi All rights reserved.//					Author:Yushin Hozumi// ===========================================================================package	StudioRAIN;import StudioRAIN.*;import StudioRAIN.geometry.*;import StudioRAIN.chaos.*;import StudioRAIN.MMI.ColorPicker.*;import StudioRAIN.MMI.Broadcast.*;import java.awt.*;public class chaos2DApp extends java.applet.Applet{	private ChaosDisplay mChaosDisplay = null;	private ChaosControls mControls = null;	public void init()	{		setLayout( new BorderLayout() );		String at = getParameter("wait");		int wait = ( at != null ) ? Integer.valueOf( at ).intValue() : 10;		mChaosDisplay = new ChaosDisplay( wait, new KawakamisWingChaos(), new Matrix2D( 10.0F, 10.0F, 10.0F, -10.0F )  );		add( "Center", mChaosDisplay );		add( "North", mControls = new ChaosControls( mChaosDisplay ) );	}		public void start()	{		mChaosDisplay.start();		mControls.enable( true );	}	public void stop()	{		mControls.disable();		mChaosDisplay.stop();	}}class ChaosCanvas extends Canvas implements Runnable{//	private ChaosControls mChaosControls = null; 	private ChaosGenerator2D mGenerator = null;	private Thread kicker = null;	private int wait = 1;	private Image offScreen = null;	private Vector2D mPoint = new Vector2D( 1.0F, 0.0F );//	private Vector2D mScale = null;	private Matrix2D mScale = null;	private int mSize = 2;	private Color mColor = Color.black;	private int mSpeed = 8;	public ChaosCanvas( int inWait, ChaosGenerator2D inGenerator, /*Vector2D*/Matrix2D inScale  )	{		wait = inWait;		mGenerator = inGenerator;		mScale = inScale;	}		// query functions	public int getWidth() { return size().width; }	public int getHeight() { return size().height; }	public void setSpeed( int inSpeed ) { mSpeed = inSpeed; }	public void setSize( int inSize ) { mSize = inSize; }	public void setPoint( Vector2D inPoint ) { mPoint = inPoint; }	public void setColor( Color inColor ) { mColor = inColor; }	public void setGenerator( ChaosGenerator2D inGenerator, /*Vector2D*/Matrix2D inScale  )	{		mGenerator = inGenerator;		mScale = inScale;	}	public String getScript() { return mGenerator.getScript(); }	private void getNextPoint()	{		mPoint = mGenerator.transform( mPoint );	}		private void drawPoint()	{		Graphics g = offScreen.getGraphics();		Vector2D thePoint = mScale.linearTransform( mPoint );		//		int x = ( int )( mPoint.getX() * mScale.getX() ) + 200;//		int y = ( int )( mPoint.getY() * mScale.getY() ) + 200;		int x = ( int )thePoint.getX() + 200;		int y = ( int )thePoint.getY() + 200;				g.setColor( mColor );		g.fillOval( x - mSize, y - mSize, mSize + mSize, mSize + mSize );		g.setColor( Color.white );		g.drawLine( x, y, x, y );	}		public boolean mouseDown( Event inEvent, int x, int y )	{		setPoint( mScale.inverse().linearTransform( new Vector2D( ( float )( x - 200 ), ( float )( y - 200 ) ) ) );		drawPoint();		return true;	}	public void clear()	{		offScreen = createImage( 400, 400 );	}	public void paint( Graphics g )	{		if( offScreen != null )		{			try			{				g.drawImage( offScreen, 0, 0, this );			}			catch( Exception e )			{				System.out.println( e.getMessage() );			}		}	}	public void start()	{		if( kicker == null)		{			if( offScreen == null )				offScreen = createImage( 400, 400 );			kicker = new Thread(this);			kicker.start();		}	}	public void stop()	{		if( kicker != null )		{			kicker.stop();			kicker = null;		}	}	public void run()	{		Thread.currentThread().setPriority( Thread.NORM_PRIORITY-1 );		while( kicker != null )		{//			System.out.println( "X = " +  x + "Y = " +  y);			for( int i = 0; i < mSpeed; i++ )			{				drawPoint();				getNextPoint();			}						paint( getGraphics() );			try			{				kicker.sleep( wait );			}			catch( InterruptedException e )			{				System.out.println( e.getMessage() );				break;			}		}	}   	public void update( Graphics g )	{		paint( g );	}}class ChaosDisplay extends Panel //implements ColorGetter{ 	private ChaosCanvas mChaosCanvas = null;	private TextArea mChaosScript = null;	private Scrollbar mSpeednBar = null;   	public ChaosDisplay( int inWait, ChaosGenerator2D inGenerator, /*Vector2D*/Matrix2D inScale )    {		setLayout( new BorderLayout() );		add( "Center", mChaosCanvas = new ChaosCanvas( inWait, inGenerator, inScale ) );		mChaosScript = new TextArea( 5, 80 );		mChaosScript.setEditable( false );		mChaosScript.setText( mChaosCanvas.getScript() );		add( "North", mChaosScript );		add( "South", mSpeednBar = new Scrollbar( Scrollbar.HORIZONTAL, 4, 8, 0, 32  ) );//		mChaosScript.repaint();    }	public void start() { mChaosCanvas.start(); }	public void stop() { mChaosCanvas.stop(); }    public boolean handleEvent( Event ev )    {//    	System.out.println( ev.target.toString() );		if( ev.target instanceof Scrollbar )		{			if( ev.target == mSpeednBar )			{//    			System.out.println( String.valueOf( mGravityBar.getValue() ) );				mChaosCanvas.setSpeed( mSpeednBar.getValue() );				return true;			}		}				return false;    }	public void setGenerator( ChaosGenerator2D inGenerator, /*Vector2D*/Matrix2D inScale )	{		mChaosCanvas.setGenerator( inGenerator, inScale );		mChaosScript.setText( mChaosCanvas.getScript() );	}	public void clear() { mChaosCanvas.clear(); }	public void setColor( Color inColor ) { mChaosCanvas.setColor( inColor ); }}class ChaosControls extends Panel implements Listener{	private ChaosDisplay mChaosDisplay = null;	private ColorCheck mColorCheck = null;    public ChaosControls( ChaosDisplay inDisplay  )    {		setLayout( new FlowLayout() );		mChaosDisplay = inDisplay;		Choice c = new Choice();		c.addItem("Wing");		c.addItem("Net");		c.addItem("Flower");		c.addItem("Ring");		c.addItem("Ikeda");		c.addItem("Lorenz");		c.addItem("Chossat And Golubitsky");		add( c );		mColorCheck = new ColorCheck();		mColorCheck.addListener( this );		mChaosDisplay.setColor( mColorCheck.getColor() );		add( mColorCheck );		add( new Button( "clear" ) );    }	public void	listenToMessage( Object inClient, BroadcastingMessage inMessage )	{		if( inMessage == ColorPicker.MessageColorChanged && inClient == mColorCheck )			mChaosDisplay.setColor( mColorCheck.getColor() );	}    public boolean action( Event ev, Object arg )    {//		if( ev.target == mColorCheck )		{//			mChaosDisplay.setColor( mColorCheck.getColor() );//			return true;		}		/*else*/ if( ev.target instanceof Choice )		{		    if( "Wing".equals( arg ) )		    {				mChaosDisplay.setGenerator( new KawakamisWingChaos(), new Matrix2D( 10.0F, 10.0F, 10.0F, -10.0F ) );				return true;		    }		    else if( "Net".equals( arg ) )		    {				mChaosDisplay.setGenerator( new KawakamisNetChaos( 0.2F ), new Matrix2D( 10.0F, 0.0F, 0.0F, 10.0F ) );				return true;		    }		    else if( "Flower".equals( arg ) )		    {				mChaosDisplay.setGenerator( new KawakamisFlowerChaos( -1.92F ), new Matrix2D( 2.0F, 2.0F, -14.0F, 14.0F ) );				return true;		    }		    else if( "Ring".equals( arg ) )		    {				mChaosDisplay.setGenerator( new KawakamisRingChaos( -0.8F ), new Matrix2D( 2.0F, 2.0F, -3.0F, 3.0F ) );				return true;		    }		    else if( "Ikeda".equals( arg ) )		    {				mChaosDisplay.setGenerator( new IkedasChaos(0.84F, 0.95F ), new Matrix2D( 100.0F, 0.0F, 0.0F, -100.0F ) );				return true;		    }		    else if( "Lorenz".equals( arg ) )		    {				mChaosDisplay.setGenerator( new LorenzChaos( 1.25F, 0.72F ), new Matrix2D( 40.0F, 0.0F, 0.0F, -40.0F ) );				return true;		    }		    else if( "Chossat And Golubitsky".equals( arg ) )		    {				mChaosDisplay.setGenerator( new ChossatGolubitskyChaos( -1.0F, 0.1F, 1.6F, -0.8F ), new Matrix2D( 100.0F, 0.0F, 0.0F, -100.0F ) );				return true;		    }			else			{				return false;			}		}		else if( ev.target instanceof Button )		{			if( "clear".equals( arg ) )		    {				mChaosDisplay.clear();				return true;		    }			else			{				return false;			}		}		else		{			return false;		}    }}/*class TriWingAttractor extends KawakamisChaos{	public TriWingAttractor()	{		super( 1.0F, -0.97F, 0.0F, 5.0F, 1.0F, -5.0F, -0.995F );	}	public String getScript()	{		return super.getScript() +			"画面のどこをクリックしても、最終的には３枚羽のパターンに収束していきます。";	}}*/