Java Paint方法闪烁并消失

问题描述:

嗨我一直在尝试通过改变我提出的mandelbrot集的程序来搅乱Java GUI,但是当我在paint方法中放置if语句时,它会使图像在屏幕,然后抹去黑屏。Java Paint方法闪烁并消失

这是我的paint方法:

public void paintComponent(Graphics g) 
{ 
    if (clicked == false && count == 0) 
    { 

     drawMandelbrot(g); //sends graphics object to the method that draws the Mandelbrot set 
     clicked = !clicked; 
    } 

    zoom(g); 
    repaint(); 

} 

public void zoom(Graphics g) 
{ 

    if (count > 0 && clicked == false) 
    { 
     g.setColor(Color.white); 
     g.fillRect(0,0, 400, 400); 

     clicked = !clicked; 
    } 
} 

我知道,因为它的工作之前有提错的drawMandelbrot()函数,并且我知道,它不应该是因为计数变焦()函数仅在mousePressed时增加。

有什么想法?我尝试过评论这么多部分,有时会留在屏幕上,但我再次运行它,但没有。 Swing/AWT这个不可靠吗?

UPDATE:

我想通了,这个问题曾与设置背景颜色做。我在主函数中设置了框架的背景颜色,但由于某种原因(我仍然不知道)在绘制图像之后,它将背景颜色再次设置在其上。

public Mandelbrot (int w, int h) //constructor method that is only utilized to bring in the size of the screen 
{ 
    this.setBackground(Color.BLACK); 
    addMouseListener(this); 
    clicked = false; 
    count = 0; 
} 

public void paintComponent(Graphics g) 
{ 
    super.paintComponent(g); 
    if (clicked == false && count == 0) 
    { 

     drawMandelbrot(g); //sends graphics object to the method that draws the Mandelbrot set 
     clicked = !clicked; 
    } 

    zoom(g); 

} 

public void zoom(Graphics g) 
{ 

    if (count > 0 && clicked == false) 
    { 
    } 
} 
public void mouseReleased(MouseEvent e) 
{ 
     zoomX = e.getX(); 
     count ++; 
     clicked = !clicked; 
     repaint(); 
     System.out.print(clicked); 
} 

更新2: 它仍然不能正常工作,它的工作是第一次,但我试图再次运行它,同样的事情发生以前一样,它采用了黑色边框结束。

+0

是不是paintComponent()更新`clicked`变量使得zoom()中的检查不会触发? – 2011-02-05 21:32:48

+0

看到paintComponent()方法中的repaint()调用会伤害我的眼睛,如果JVM不智能,会导致不停的递归。为什么试图在那里调用这个方法? – 2011-02-05 22:54:01

在方法调用的顶部调用super.paintComponent()以使Swing句柄绘制组件的其余部分。有关painting components in Swing的更多信息,请参阅此文章。但基本上,paintComponent()方法正在绘制您尝试显示的组件的实际工作,当您覆盖它时,所有组件都会被禁用。通过调用super.paintComponent()你有Swing做它需要做的事情来正确绘制一切,然后它绘制你想绘制的东西。

更新 我想知道这是不是与你的逻辑有关的“点击”。当你打电话给repaint()时,它从头开始重新整修整个面板。这意味着如果你想要一些东西持续存在,你需要a)不要打电话重画,也不要让Swing调用重画,例如调整窗口大小;或者b)确保你的重绘方法总是能绘制你想要的东西。一般来说,b)是更好的方法,因为它更健壮。

因此,我会让你尝试重构你的代码,使其在paintComponent()方法中没有任何条件,这样无论调用多少次,该对象仍然会被绘制。

您可能遇到的问题(大概这就是为什么您按照您的方式构建代码的原因)是构建要绘制的对象所花费的时间可能太长,无法一直重绘。如果这是一个问题,则需要重新编写程序的逻辑,以便计算想要在另一个线程中绘制的内容(请参见SwingUtilities.invokeLater()),然后在调用paintComponent()时只需绘制之前计算的值。

将一个System.out.println(清单中的相关变量);在每个方法的开始,所以你得到它是存在的秩序的清晰画面。

这将是有益的知道zoom(g)会发生什么,你没有包括那个。

您也可以更正帖子,以便mouseReleased方法的格式正确。我第一次错过了! :)

一些逻辑似乎有点...如果。

这两个if语句检查clicked==false但这只会是每个鼠标释放后第一个paintComponent。我不是一个Swing专家,我只能基于AWT的知识,但是不会经常调用paintComponent函数吗?它可能画一次,然后被召回,并再次绘画 - 只有这一次(clicked==false)是真实的。因此,'闪光'。

我会建议将mandlebrot绘制到图像上,然后使用getGraphics().drawImage(img, 0, 0 null);将图像复制到组件上,然后您只需在每个油漆中将现成的图像曝光。

以下代码完全未经测试。我对此不承担任何责任。 ;-)

BufferedImage mbrot = null; 
public void paintComponent(Graphics g) 
{ 
    super.paintComponent(g); 
    if (mbrot==null || mbrot.getWidth()!=getWidth() || mbrot.getHeight()!=getHeight()) 
    { 
     mbrot = new BufferedImage(getWidth(), getHeight(), null); 
    } 
    if (clicked == false) 
    { 
     Graphics mg = mbrot.getGraphics(); 
     if (count==0) 
     { 
      drawMandelbrot(mg); //sends graphics object to the method that draws the Mandelbrot set 
      clicked = !clicked; 
     } 
     else 
     { 
      zoom(mg); 
     } 
     mg.dispose(); 
    } 
    g.drawImage(mbrot, 0, 0, null); 
}