Using Java's JComponent repaint()

大憨熊 提交于 2019-12-07 12:20:12

问题


I'm writing a simple Game of Life program in Java and am having a bit of trouble getting it to animate. I've got a JComponent class called LifeDraw, which displays a grid of pixels, with the following paint method:

protected void paintComponent(Graphics g) {
    super.paintComponent(g);

    for (int y = 0; y < lGrid.getHeight(); y++) {
        for (int x = 0; x < lGrid.getWidth(); x++) {
            if (lGrid.getCell(x,y) == 1) {
                g.setColor(Color.red);
                g.fillRect(x * lGrid.getSqSize(), y * lGrid.getSqSize(), lGrid.getSqSize(), lGrid.getSqSize());
            } else {
                g.setColor(Color.white);
                g.fillRect(x * lGrid.getSqSize(), y * lGrid.getSqSize(), lGrid.getSqSize(), lGrid.getSqSize());
            }
        }
    }
}

And then another class LifeGrid that has a method run(), which when called will update the grid of pixels for one generation and then call LifeDraw.repaint(). However, if I try to call run() in a loop, the JComponent doesn't repaint until the loop is finished so all that is ever displayed is the first generation and the last one. I figured it was probably just updating too quickly to repaint, so I tried using Thread.sleep() between iterations but still had the same problem. Theoretically (or at least I was hoping it would), it should repaint the component between each iteration and display an animation of the pixels changing.

I'm not that well versed in Java GUI, so any help would be really appreciated. Hopefully I've explained it clearly enough, let me know otherwise!


回答1:


I don't know if it would solve your problem, but you could try calling run() from a Timer instead of a simple for or while loop.




回答2:


From the JavaDocs for repaint():

Adds the specified region to the dirty region list if the component is showing. The component will be repainted after all of the currently pending events have been dispatched.

All repaint does is signal that the area needs repainting.
Try paintImmediately or update.




回答3:


Repaint has to be fired in the event loop, not in another thread.
Try replacing your call to repaint() with following code:

SwingUtilities.invokeLater(new Runnable()
{
    public void run()
    {
        repaint();
    }
}); 


来源:https://stackoverflow.com/questions/2015795/using-javas-jcomponent-repaint

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!