SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

Javaで学ぶグラフィックス処理

2次元カオス図形を芸術的に描画する

エノン写像、グモウスキー・ミラ写像の探索


  • X ポスト
  • このエントリーをはてなブックマークに追加

プログラム

 エノン写像とグモウスキー・ミラ写像のプログラムは非常に似ていますので、エノン写像は省略しないで全体を示し、グモウスキー・ミラ写像は、エノン写像との相違点のみを示します。

エノン写像

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

public class Henon extends Applet implements
   AdjustmentListener,ActionListener{

   Scrollbar scrollbar;
   Label label;
   Button button=new Button("再描画");

   int SIZE=400;
   double a;

   int X0=210;
   int Y0=260;

   public void init(){

      setLayout(new BorderLayout());
      Panel panel=new Panel();
      panel.setLayout(new GridLayout(2,2,5,5));
      add(panel,"North");

      //スクロールバーの範囲を0~100にする
      scrollbar=new Scrollbar(Scrollbar.HORIZONTAL,50,5,0,105);

      label=new Label();

      panel.add(label);
      panel.add(new Label("      "));

      panel.add(scrollbar);
      panel.add(button);

      scrollbar.addAdjustmentListener(this);
      button.addActionListener(this);

      a=0.5;    //起動時の初期設定

   }

   public void paint(Graphics g){

      double x,y,yxx,temp;
      int xx,yy,k;

      label.setText("alpha="+String.valueOf((float)a)+"π");

      //仮のパラメータaを実際のパラメータαに変換する
      //高速化のために、あらかじめ三角関数を求めておく
      double sin_a=Math.sin(Math.PI*a);
      double cos_a=Math.cos(Math.PI*a);

      //背景を黒で描く
      g.setColor(Color.black);
      g.fillRect(X0-SIZE/2,Y0-SIZE/2,SIZE,SIZE);

      // ------------------ Henon's Mapping-------------------

      for(int j=0;j<=80;j++){

         //初期値を乱数で与える(範囲は-1~1)
         x=2.0*(Math.random()-0.5);
         y=2.0*(Math.random()-0.5);


         //着色の色を決める
         k=(int)(256*(x*x+y*y));
         Color color=changeToColor(k,128);
         g.setColor(color);

         //写像の繰り返し
         for(int i=0;i<5000;i++){

            yxx=y-x*x; //y-x*x*x; y-0.8*Math.sin(x); y-0.1/x; も試した
            temp=x*cos_a-yxx*sin_a;
            y=x*sin_a+yxx*cos_a;
            x=temp;
         
            if(Math.abs(x)<1.6 && Math.abs(y)<1.6){
               xx=X0+(int)(SIZE/3.2*x);
               yy=Y0-(int)(SIZE/3.2*y);
               g.drawLine(xx,yy,xx,yy);
            }           

         }

      }

      // -----------------------------------------------------

   }

   //スクロールバーが変更されたら値を読み取って再描画するメソッド
   public void adjustmentValueChanged(AdjustmentEvent ae){

      //スクロールバーの値を仮のパラメータaに変換する
      a=scrollbar.getValue()/100.0;
      repaint();

   }

   //ボタンがクリックされたら再描画するメソッド
   public void actionPerformed(ActionEvent ae){

      repaint();

   }

   //数値を色に変換するメソッド
   public Color changeToColor(int i,int color_base){

      int d=i % color_base;
      float h=(float)d/color_base;

      return Color.getHSBColor(h,1.0f,1.0f);

   }
             
}

グモウスキー・ミラ写像

 エノンモデルとの相違点のみを示します。

//スクロールバーの範囲を0~200にする
scrollbar=new Scrollbar(Scrollbar.HORIZONTAL,100,5,0,205);

a=0.0;     //起動時の初期設定

//高速化のために、定数をあらかじめ求めておく
double aa=2.0*(1-a);

label.setText("a="+String.valueOf((float)a));

// -----------------Gumowsky-Mira's Mapping--------------

for(int j=0;j<=20;j++){

   //初期値を乱数で与える(範囲は-20~20)
   x=40.0*(Math.random()-0.5);
   y=40.0*(Math.random()-0.5);

   //着色の色を決める
   //k=(int)(40*Math.max(x,y)); (int)(100*Math.atan(y/x); も試した
   k=(int)(x*x+y*y);
   Color color=changeToColor(k,256);
   g.setColor(color);

   u=a*x+aa*x*x/(1+x*x);    //初期値のみの処理、

   for(int i=0;i<10000;i++){

      x1=y+u;        //古い u を使用
      xx1=x1*x1;     //高速化処理
      u=a*x1+aa*xx1/(1+xx1);
      y=-x+u;        //新しい u を使用
      x=x1;

      if(Math.abs(x)<40.0 && Math.abs(y)<40.0){

         xx=X0+(int)(SIZE/80.0*x);
         yy=Y0-(int)(SIZE/80.0*y);
         g.drawLine(xx,yy,xx,yy);

      }           

   }

// ------------------------------------------------------

//スクロールバーの値をパラメータaに変換する
a=(scrollbar.getValue()-100)/100.0;

プログラムの使い方

 エノン写像とグモウスキー・ミラ写像の2つのプログラムに共通していますが、アプレットを起動すると、上部にパラメータ変更用のスライダーと、下部にカオス図形が現れます。スライダーを動かすと、自動的に図形が描画されます。xとyの初期値は乱数によって限られた個数しか発生しませんので、そのつど異なった図形が現れます。[再描画]ボタンを何回かクリックして、美しいと思われる図形を探索して下さい。

次のページ
プログラムの実行結果

修正履歴

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
Javaで学ぶグラフィックス処理連載記事一覧

もっと読む

この記事の著者

石立 喬(イシダテ タカシ)

1955年東京工大卒。同年、NECへ入社し、NEC初のコンピュータの開発に参画。磁気メモリ、半導体メモリの開発、LSI設計などを経て、1989年帝京大学理工学部教授。情報、通信、電子関係の教育を担当。2002年定年により退職し現在に至る。2000年より、Webサイト「Visual C++の勉強部屋」を公開。...

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/327 2008/03/16 10:38

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング