Java 如何从其他类绘制到JPanel(类扩展)
我的确有一个错误Java 如何从其他类绘制到JPanel(类扩展),java,swing,jpanel,java-2d,Java,Swing,Jpanel,Java 2d,我的确有一个错误 public class Main extends JPanel implements Runnable { private static final int WIDTH = 1000; private static final int HEIGHT = 800; TerranGenartor gen = new TerranGenartor(); public Main() { setSize(WIDTH, HEIGHT);
public class Main extends JPanel implements Runnable {
private static final int WIDTH = 1000;
private static final int HEIGHT = 800;
TerranGenartor gen = new TerranGenartor();
public Main() {
setSize(WIDTH, HEIGHT);
gen.run();
}
public void paintComponents(Graphics g) {
repaint();
}
public void run() {
}
}
我的terrangenerator
职业
TerranGenartor gen = new TerranGenartor();
public class TerranGenartor implements Runnable {
Main main = new Main();
Graphics g;
Random r = new Random();
int SMIN = 1;
int SMAX = 3;
int i = 0;
int num;
int x = 0;
int y = 0;
public Color grass = new Color(124, 252, 0);
public Color stone = new Color(190, 190, 190);
public Color dirt = new Color(139, 69, 19);
boolean Runn = false;
public void start() {
Runn = true;
System.out.println("Working...");
}
public TerranGenartor() {
Runn = true;
}
protected void paintComponent(Graphics g) {
g = main.getGraphics();
while (Runn) {
if (i <= 1000) {
num = r.nextInt(SMAX - SMIN + 1) + SMIN;
switch (num) {
case 1:
g.setColor(grass);
break;
case 2:
g.setColor(stone);
break;
case 3:
g.setColor(dirt);
break;
default:
g.setColor(grass);
break;
}
g.fillRect(x, y, 50, 50);
x += 50;
System.out.println(i);
System.out.println("X: " + x);
try {
Thread.sleep(15);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
public void run() {
while (Runn) {
paintComponent(g);
}
}
}
这门课只是遵守并运行它,我认为一切都很好
问题是,当我想从TerranGenerator
类中绘制时,它不起作用。JPanel上没有显示任何内容
让我们从
setSize(宽度、高度)代码>来自Main
。这是个坏主意。布局管理器可以覆盖这些值(假设您正在使用布局管理器)。您应该重写getPreferredSize
并将它们返回到那里
public class The_Runner {
Main main = new Main();
JFrame frame = new JFrame();
private static final int WIDTH = 1000;
private static final int HEIGHT = 800;
String TITLE = "Map gen.";
public The_Runner() {
frame.setSize(WIDTH, HEIGHT);
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLocationRelativeTo(null);
frame.setResizable(false);
frame.setTitle(TITLE);
frame.add(main);
}
public static void main(String[] args) {
The_Runner runner = new The_Runner();
}
}
然后这个(也来自Main
)
决不能从paint
方法中调用repaint
,也不能调用任何可能导致调用repaint
的方法,否则将陷入一个无限循环的厄运,将使CPU循环高达100%
在Main
和terrangenerator
之间有一个循环引用。基本上,您已经在每个类中声明了每个类的引用,编译器无法处理这个问题,因为它无法在不先构建另一个类的情况下构建一个类
永远不要这样做
public void paintComponents(Graphics g) {
repaint();
}
getGraphics
is可以返回null
值。此方法返回的结果值只不过是应用程序使用的当前图形上下文的快照。这可以在下一个绘制周期中取消引用或更改
永远不要从事件调度线程(EDT)外部绘制/更新/修改/创建任何Swing组件,如果这样做的话,您可能最终会得到奇怪的绘制工件,因为您尝试更新图形,EDT也会更新它,这永远都不漂亮
你可能想看看
已更新
我怀疑您的“主要”问题(除了代码无法编译之外)将是repaint
请求正在清除您使用main.getGraphics
您还应该在Main#paintComponent
方法中调用super.paintComponent
用示例更新
1)要更快地获得更好的帮助,请发布一个。2) 使用BufferedImage
作为画布通常更容易进行自定义渲染。该源中过多的空白“空白”行是怎么回事?只需要一行空白,源代码中的大多数代码都不能提高可读性,而且没有一行可以加快代码的运行速度。很抱歉,这是我第一个被问到的问题,对这个网站来说很新。重要的不是第一次就把它做好,而是从经验中学习。欢迎来到SO.:)
public void paintComponents(Graphics g) {
repaint();
}
g = main.getGraphics();