【发布时间】:2019-06-15 12:34:38
【问题描述】:
我最初制作的程序如下。我使用 extends Canvas 和 update 方法来不断地绘制更多的点。我的理解是,每次调用 repaint() 时,都会通过使用 update() 方法将新点添加到现有的 Canvas 上。如果每次调用 repaint() 时方法是 paint() 而不是 update(),它将绘制一个只有 50 个点的新 Canvas。这是我的 BarnsleyFern 类,它扩展了 Canvas。
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Color;
import java.awt.Canvas;
import java.lang.Math;
import java.awt.event.*;
import javax.swing.*;
public class BarnsleyFern extends Canvas
{
private double newX,x=0;
private double newY,y=0;
public BarnsleyFern(int width, int height)
{
setBackground(Color.BLACK);
setSize(width,height);
setVisible(true);
ActionListener action = new ActionListener()
{
public void actionPerformed(ActionEvent event)
{
repaint();
}
};
Timer timer = new Timer(100,action);
timer.start();
}
public void update(Graphics window)
{
Graphics2D g2d = (Graphics2D)window;
window.translate(360,800);
//g2d.rotate(Math.toRadians(180));
fern(window);
}
public void fern(Graphics window)
{
Color newColor = new Color((int)(Math.random()*256),(int)(Math.random()*256),(int)(Math.random()*256));
for(int i=0;i<50;i++)
{
window.setColor(Color.BLUE);
int rand = (int)(Math.random()*100);
if(rand<1)
{
newX=0;
newY=0.16*y;
}
else if(rand<86)
{
newX=0.85*x + 0.04*y;
newY=0.85*y - 0.04*x + 1.6;
}
else if(rand<93)
{
newX=0.20*x - 0.26*y;
newY=0.23*x + 0.22*y + 1.6;
}
else
{
newX=0.28*y - 0.15*x;
newY=0.26*x + 0.24*y + 0.44;
}
window.fillOval((int)(newX*165.364),-(int)(newY*80.014),2,2);
x=newX;
y=newY;
}
}
}
以下代码是扩展 JFrame 的 BarnsleyFernRunner 类。这将设置 JFrame 并包含 main 方法。
import javax.swing.JFrame;
public class BarnsleyFernRunner extends JFrame
{
public BarnsleyFernRunner()
{
setTitle("Barnsley Fern");
setSize(800,800);
add(new BarnsleyFern(800,800));
setVisible(true);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public static void main(String[] args)
{
BarnsleyFernRunner runner = new BarnsleyFernRunner();
}
}
然后我决定通过扩展 JPanel 而不是扩展 Canvas 来稍微更改我的代码。我选择这样做是因为 JPanel 和 JFrame 都来自 javax.swing 包。新的 BarnsleyFern 类使用上面的 BarsnleyFernRunner 类。这个类的工作方式与以前不同。每次调用 repaint() 时,都会绘制五十个新点,而旧点会消失。我的理解是这种情况是因为每次调用 repaint() 都会创建一个新的 JPanel。我的问题是如何在 JPanel 中调用 repaint() 方法而不创建全新的 JPanel。有没有办法在不“擦除”我已经绘制的内容的情况下调用 repaint() 。有没有办法可以使用 update() 方法复制我在第一堂课中所做的事情。这是我的 BarnsleyFern 类,它扩展了 JPanel
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Color;
import java.awt.Canvas;
import java.lang.Math;
import java.awt.event.*;
import javax.swing.*;
public class BarnsleyFern extends JPanel
{
private double newX,x=0;
private double newY,y=0;
public BarnsleyFern(int width, int height)
{
setBackground(Color.BLACK);
setSize(width,height);
setVisible(true);
ActionListener action = new ActionListener()
{
public void actionPerformed(ActionEvent event)
{
repaint();
}
};
Timer timer = new Timer(100,action);
timer.start();
}
public void paintComponent(Graphics window)
{
super.paintComponent(window);
Graphics2D g2d = (Graphics2D)window;
window.translate(360,800);
//g2d.rotate(Math.toRadians(180));
fern(window);
}
public void fern(Graphics window)
{
Color newColor = new Color((int)(Math.random()*256),(int)(Math.random()*256),(int)(Math.random()*256));
for(int i=0;i<50;i++)
{
window.setColor(Color.BLUE);
int rand = (int)(Math.random()*100);
if(rand<1)
{
newX=0;
newY=0.16*y;
}
else if(rand<86)
{
newX=0.85*x + 0.04*y;
newY=0.85*y - 0.04*x + 1.6;
}
else if(rand<93)
{
newX=0.20*x - 0.26*y;
newY=0.23*x + 0.22*y + 1.6;
}
else
{
newX=0.28*y - 0.15*x;
newY=0.26*x + 0.24*y + 0.44;
}
window.fillOval((int)(newX*165.364),-(int)(newY*80.014),2,2);
x=newX;
y=newY;
}
}
}
【问题讨论】:
-
不要做
super.paintComponent
标签: java jframe jpanel paintcomponent repaint