方格的是一个矩形,需要继承Rectangle2D类,使用它的静态内部类Float的原因是它比静态内部类Double精度小。
人的眼睛或者是计算机的渲染图形是不会显示那些计算中很低的位的,所以采用计算Float更快。
package yumu.chaos.lifegame.gui; import java.awt.geom.Rectangle2D; public class LifeRect extends Rectangle2D.Float { public LifeRect(float x, float y, float w, float h) { super(x, y, w, h); } }
在构造函数中通过Toolkit获取了屏幕的宽与高,把窗体显示在屏幕的中央。
设置窗体的标题和图标,这里可能是图片本身的问题,设置了的图标并没有显示在窗体上。
设置窗口关闭的时候退出应用,设置窗口可见。
package yumu.chaos.lifegame.gui; import java.awt.Component; import java.awt.Dimension; import java.awt.Image; import java.awt.Toolkit; import javax.swing.ImageIcon; import javax.swing.JFrame; public class GameFrame extends JFrame { public GameFrame(int width, int height) { Toolkit toolkit = Toolkit.getDefaultToolkit(); Dimension dimension = toolkit.getScreenSize(); int screenWidth = dimension.width; int screenHeight = dimension.height; setTitle("Conway Cellular Automata"); Image image = new ImageIcon("logo-icon.jpg").getImage(); setIconImage(image); setLocation(screenWidth/2 - width/2, screenHeight/2 - height/2); setSize(width + 30, height + 50); setResizable(false); setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); setVisible(true); } @Override public void remove(Component comp) { if(comp != null) super.remove(comp); } }
构造函数中设置了需要绘制的数据,这个数据是从世界的存活细胞图方法中获得的。
确定方格的单位宽度和单位高度,存活显示为黑色,死亡显示为白色,周围用浅灰色绘制方格的边框。
画笔和画纸的行为被放置在Graphics2D的对象g2中,这里设置画笔的颜色设置的是g2的内容。
package yumu.chaos.lifegame.gui; import java.awt.Color; import java.awt.Dimension; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.Paint; import javax.swing.JPanel; public class DrawPanel extends JPanel{ private boolean[][] arr; private int width; private int height; public DrawPanel(boolean[][] arr, int width, int height){ this.arr = arr; this.width = width; this.height = height; } @Override public void paint(Graphics g) { Graphics2D g2 = (Graphics2D) g; int lenX = arr.length; int lenY = arr[0].length; float unitX = (float)width / lenX; float unitY = (float)height / lenY; for (int x = 0; x < lenX; ++x) { for (int y = 0; y < lenY; ++y) { Paint paint = arr[x][y] ? Color.BLACK : Color.WHITE; LifeRect rect = new LifeRect(unitX * x, unitY * y, unitX, unitY); g2.setPaint(paint); g2.fill(rect); g2.setPaint(Color.LIGHT_GRAY); g2.draw(rect); } } } @Override public Dimension getPreferredSize() { return new Dimension(width, height); } }
画者默认有自己的一个画板框架,调用绘制方法时,会把当前的画板卸下来,并安置好新的画板。
新的画板已经预设好了图像,只是看起来还是一张白纸,最后画板框架使画板中的图像显示出来。
下次的绘制中会重复,卸下白纸,粘上新白纸,显示图像的过程。
package yumu.chaos.lifegame.gui; public class Painter { private static final int DEFAULT_WIDTH = 500; private static final int DEFAULT_HEIGHT = 500; private GameFrame frame; private DrawPanel panel; public Painter() { frame = new GameFrame(DEFAULT_WIDTH, DEFAULT_HEIGHT); } public void paint(boolean[][] arr){ frame.remove(panel); panel = new DrawPanel(arr, DEFAULT_WIDTH, DEFAULT_HEIGHT); frame.add(panel); frame.paintAll(panel.getGraphics()); } }
static int[][] LOVE = { {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, {0,1,1,1,0,0,0,1,0,0,0,0,1,1,0,0,1,0,0,0,1,0,1,1,1,0,0,0,1,0,0,1,0}, {0,0,1,0,0,0,0,1,0,0,0,1,0,0,1,0,1,0,0,0,1,0,1,0,0,0,0,0,1,0,0,1,0}, {0,0,1,0,0,0,0,1,0,0,0,1,0,0,1,0,0,1,0,1,0,0,1,1,1,0,0,0,1,0,0,1,0}, {0,0,1,0,0,0,0,1,0,0,0,1,0,0,1,0,0,1,0,1,0,0,1,0,0,0,0,0,1,0,0,1,0}, {0,1,1,1,0,0,0,1,1,1,0,0,1,1,0,0,0,0,1,0,0,0,1,1,1,0,0,0,0,1,1,0,0}, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0} };
当种子为LOVE时,运行:deus.createWorld(transpose(LOVE));
[混沌,awt和swing绘制平面图形简介](http://www.cnblogs.com/kodoyang/p/Chaos_Graphics2D_Awt_Swing.html)
[混沌,细胞自动机与生命游戏](http://www.cnblogs.com/kodoyang/p/Chaos_ConwayCellularAutomata_GameOfLife.html)
本篇是上一篇日志『混沌,细胞自动机与生命游戏』的图形绘制部分。
请点击正下方的『关注我』关注我!点击右下方的推荐图标推荐这片日志!
本文地址:http://www.cnblogs.com/kodoyang/p/Chaos_ConwayCellularAutomata_GameOfLife_GraphDrawing.html
雨木阳子
2015年8月17日