简体   繁体   English

Java:repaint()无法正常工作?

[英]Java: repaint() not working?

Code: 码:

@Override
    public void mouseReleased(MouseEvent e) { //when the mouse is pressed
        Point where=e.getPoint();
        int x=(where.x-3)/20+1;
        int y=(where.y-30)/20+1;
        if(x>=1&&x<=30&&y>=1&&y<=30)
        {
            v[x][y]=1-v[x][y];
            repaint();
            try{
            TimeUnit.MILLISECONDS.sleep(300);
            }
            catch(Exception ex){}
            redo();
            repaint();
        }
    }

The paint function is made so that it will show, on screen, all 30x30 elements of the V matrix. 绘制功能的制作使其可以在屏幕上显示V矩阵的所有30x30元素。 The redo function makes some changes (the details are irrelevant) to V. 重做功能对V进行了一些更改(细节无关)。

What i am trying to do is paint the elements of V, but with v[x][y] changed, wait 0.3s, and then paint the elements of V again, but this time after they were changed by the redo function. 我想做的是绘制V的元素,但是更改v [x] [y],等待0.3s,然后再次绘制V的元素,但是这次是在它们被重做功能更改之后。 But the repaint only works the second time, the first time not doing anything. 但是重新绘制只能在第二次进行,而第一次则不执行任何操作。

The sleep will block the event driven thread (EDT) - try not to sleep in the main thread of your application. 睡眠将阻止事件驱动线程(EDT)-尝试不要在应用程序的主线程中睡眠。 The EDT will render your frames / dialogs / panels, and will respond to clicks and menus and keyboard entry. EDT将渲染您的框架/对话框/面板,并响应单击,菜单和键盘输入。 It's really important to do only quick tasks on this thread. 在此线程上仅执行快速任务非常重要。

How about adding a Timer object to run code later? 如何添加一个Timer对象以稍后运行代码?

  Timer timer = new Timer(300, new ActionListener(){

     @Override
     public void actionPerformed(ActionEvent e) {
         SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
               // runs code on the EDT to edit UI elements (recommended way)
               redo();
               repaint();
            }

         });  
     }
  });
  timer.setRepeats(false);
  timer.start();

So the Timer object will create a new thread, delay for 300 milliseconds, and then call the 'actionPerformed' method. 因此,Timer对象将创建一个新线程,延迟300毫秒,然后调用“ actionPerformed”方法。 This will happen on the Timer's thread. 这将在计时器的线程上发生。 It's not recommended to change UI elements from any thread except for the EDT, so we use the invokeLater method which causes swing to run the runnable on the EDT itself - so back on the original thread. 不建议从EDT以外的任何线程更改UI元素,因此我们使用invokeLater方法,该方法导致swing在EDT本身上运行可运行对象-因此返回原始线程。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM