天天看點

Java拾遺(五)分形

Java拾遺(五)

  • 分形
      • MengerSponge的實作(僅畫出過程)

分形

MengerSponge的實作(僅畫出過程)

package drawpadListener;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.Polygon;

import javax.swing.JFrame;

public class TRY extends JFrame{
	public void paintMenger(Graphics g, int t){
		int x=100,y=600;//正方體的頂點坐标
		int d=100,dx=65,dy=50; //正方體的高,寬深度
		//畫出來
		paintOneMenger(g, x, y, d, dx, dy, t);
	}
	public void paintOneMenger(Graphics g, int x, int y, int d, int dx, int dy, int t){
		t--;//疊代次數

		//下層
		Point p00=new Point(x,y);
		Point[] ps01=getPointByP0(p00, d, dx, dy);
		Point[] ps02=getPointByP0(ps01[3], d, dx, dy);
		Point[] ps03=getPointByP0(ps02[3], d, dx, dy);
		Point[] ps04=getPointByP0(ps01[6], d, dx, dy);
		Point[] ps05=getPointByP0(ps02[6], d, dx, dy);//不畫
		Point[] ps06=getPointByP0(ps03[6], d, dx, dy);
		Point[] ps07=getPointByP0(ps04[6], d, dx, dy);
		Point[] ps08=getPointByP0(ps05[6], d, dx, dy);
		Point[] ps09=getPointByP0(ps06[6], d, dx, dy);
		draw(g, ps07[0], ps07[1], ps07[2], ps07[3], ps07[4], ps07[5], ps07[6]);
		if(t>0){
			paintOneMenger(g, ps07[0].x, (ps07[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps08[0], ps08[1], ps08[2], ps08[3], ps08[4], ps08[5], ps08[6]);
		if(t>0){
			paintOneMenger(g, ps08[0].x, (ps08[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps09[0], ps09[1], ps09[2], ps09[3], ps09[4], ps09[5], ps09[6]);
		if(t>0){
			paintOneMenger(g, ps09[1].x, (ps09[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps04[0], ps04[1], ps04[2], ps04[3], ps04[4], ps04[5], ps04[6]);
		if(t>0){
			paintOneMenger(g, ps04[1].x, (ps04[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps06[0], ps06[1], ps06[2], ps06[3], ps06[4], ps06[5], ps06[6]);
		if(t>0){
			paintOneMenger(g, ps06[1].x, (ps06[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps01[0], ps01[1], ps01[2], ps01[3], ps01[4], ps01[5], ps01[6]);
		if(t>0){
			paintOneMenger(g, ps01[1].x, (ps01[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps02[0], ps02[1], ps02[2], ps02[3], ps02[4], ps02[5], ps02[6]);
		if(t>0){
			paintOneMenger(g, ps02[1].x, (ps02[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps03[0], ps03[1], ps03[2], ps03[3], ps03[4], ps03[5], ps03[6]);
		if(t>0){
			paintOneMenger(g, ps03[1].x, (ps03[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
				
		//中間
		Point p10=new Point(p00.x, p00.y-d);
		Point[] ps11=getPointByP0(p10, d, dx, dy);
		Point[] ps12=getPointByP0(ps11[3], d, dx, dy);//不畫
		Point[] ps13=getPointByP0(ps12[3], d, dx, dy);
		Point[] ps14=getPointByP0(ps11[6], d, dx, dy);//不畫
		Point[] ps15=getPointByP0(ps12[6], d, dx, dy);//不畫
		Point[] ps16=getPointByP0(ps13[6], d, dx, dy);//不畫
		Point[] ps17=getPointByP0(ps14[6], d, dx, dy);
		Point[] ps18=getPointByP0(ps15[6], d, dx, dy);//不畫
		Point[] ps19=getPointByP0(ps16[6], d, dx, dy);
		draw(g, ps17[0], ps17[1], ps17[2], ps17[3], ps17[4], ps17[5], ps17[6]);
		if(t>0){
			paintOneMenger(g, ps17[0].x, (ps17[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps19[0], ps19[1], ps19[2], ps19[3], ps19[4], ps19[5], ps19[6]);
		if(t>0){
			paintOneMenger(g, ps19[0].x, (ps19[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps11[0], ps11[1], ps11[2], ps11[3], ps11[4], ps11[5], ps11[6]);
		if(t>0){
			paintOneMenger(g, ps11[0].x, (ps11[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps13[0], ps13[1], ps13[2], ps13[3], ps13[4], ps13[5], ps13[6]);
		if(t>0){
			paintOneMenger(g, ps13[0].x, (ps13[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
				
		//上層
		Point p20=new Point(p10.x,p10.y-d);
		Point[] ps21=getPointByP0(p20, d, dx, dy);
		Point[] ps22=getPointByP0(ps21[3], d, dx, dy);
		Point[] ps23=getPointByP0(ps22[3], d, dx, dy);
		Point[] ps24=getPointByP0(ps21[6], d, dx, dy);
		Point[] ps25=getPointByP0(ps22[6], d, dx, dy);//不畫
		Point[] ps26=getPointByP0(ps23[6], d, dx, dy);
		Point[] ps27=getPointByP0(ps24[6], d, dx, dy);
		Point[] ps28=getPointByP0(ps25[6], d, dx, dy);
		Point[] ps29=getPointByP0(ps26[6], d, dx, dy);
		draw(g, ps27[0], ps27[1], ps27[2], ps27[3], ps27[4], ps27[5], ps27[6]);
		if(t>0){
			paintOneMenger(g, ps27[0].x, (ps27[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps28[0], ps28[1], ps28[2], ps28[3], ps28[4], ps28[5], ps28[6]);
		if(t>0){
			paintOneMenger(g, ps28[0].x, (ps28[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps29[0], ps29[1], ps29[2], ps29[3], ps29[4], ps29[5], ps29[6]);
		if(t>0){
			paintOneMenger(g, ps29[0].x, (ps29[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps24[0], ps24[1], ps24[2], ps24[3], ps24[4], ps24[5], ps24[6]);
		if(t>0){
			paintOneMenger(g, ps24[0].x, (ps24[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps26[0], ps26[1], ps26[2], ps26[3], ps26[4], ps26[5], ps26[6]);
		if(t>0){
			paintOneMenger(g, ps26[0].x, (ps26[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps21[0], ps21[1], ps21[2], ps21[3], ps21[4], ps21[5], ps21[6]);
		if(t>0){
			paintOneMenger(g, ps21[0].x, (ps21[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps22[0], ps22[1], ps22[2], ps22[3], ps22[4], ps22[5], ps22[6]);
		if(t>0){
			paintOneMenger(g, ps22[0].x, (ps22[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
		draw(g, ps23[0], ps23[1], ps23[2], ps23[3], ps23[4], ps23[5], ps23[6]);
		if(t>0){
			paintOneMenger(g, ps23[0].x, (ps23[0].y+d/3*2), d/3, dx/3, dy/3, t);
		}
	}
	public void draw(Graphics g, Point p0, Point p1, Point p2, Point p3, Point p4, Point p5, Point p6){
		//g.drawLine(p0.x, p0.y, p1.x, p1.y);
		//g.drawLine(p1.x, p1.y, p2.x, p2.y);
		//g.drawLine(p2.x, p2.y, p3.x, p3.y);
		//g.drawLine(p3.x, p3.y, p0.x, p0.y);
		//g.drawLine(p2.x, p2.y, p4.x, p4.y);
		//g.drawLine(p4.x, p4.y, p5.x, p5.y);
		//g.drawLine(p5.x, p5.y, p6.x, p6.y);
		//g.drawLine(p6.x, p6.y, p0.x, p0.y);
		//g.drawLine(p3.x, p3.y, p5.x, p5.y);

		Polygon pon1 = new Polygon();
		pon1.addPoint(p0.x, p0.y);
		pon1.addPoint(p1.x, p1.y);
		pon1.addPoint(p2.x, p2.y);
		pon1.addPoint(p3.x, p3.y);
		g.setColor(new Color(255, 0, 0));
		g.fillPolygon(pon1);
		Polygon pon2 = new Polygon();
		pon2.addPoint(p0.x, p0.y);
		pon2.addPoint(p3.x, p3.y);
		pon2.addPoint(p5.x, p5.y);
		pon2.addPoint(p6.x, p6.y);
		g.setColor(new Color(180, 0, 0));
		g.fillPolygon(pon2);
		Polygon pon3 = new Polygon();
		pon3.addPoint(p2.x, p2.y);
		pon3.addPoint(p3.x, p3.y);
		pon3.addPoint(p5.x, p5.y);
		pon3.addPoint(p4.x, p4.y);
		g.setColor(new Color(120, 0, 0));
		g.fillPolygon(pon3);
	}
	public Point[] getPointByP0(Point p0, int d, int dx, int dy){
		Point p1 = new Point(p0.x, p0.y+d);
		Point p2 = new Point(p0.x+d, p0.y+d);
		Point p3 = new Point(p0.x+d, p0.y);
		Point p4 = new Point(p2.x+dx, p2.y-dy);
		Point p5 = new Point(p4.x, p4.y-d);
		Point p6 = new Point(p5.x-d, p5.y);
		Point[] ps = new Point[7];
		ps[0] = p0;
		ps[1] = p1;
		ps[2] = p2;
		ps[3] = p3;
		ps[4] = p4;
		ps[5] = p5;
		ps[6] = p6;
		return ps;
	}
}

           

疊代的方式有點蠢,不過可以指定其階數,畫出來的效果還不錯。

可以發現畫出來小正方形之間存在間隙,顔色與先被覆寫的那一層相同。這是因為Graphics是以像素為機關操作,而在做操作邊長 d/3 的操作時,d 是 int 類型,如果 d 不能整除3,就會取餘取整儲存為 int 類型給Graphics操作。