简体   繁体   English

从内部循环重绘JPanel

[英]Repaint JPanel from inside loop

Is it possible to repaint a JPanel from within a loop in another object? 是否可以从另一个对象的循环中重新绘制JPanel? I have a JFrame that consists of a JPanel (DrawPanel) and a SA object. 我有一个由JPanel(DrawPanel)和一个SA对象组成的JFrame。 I would like to update/repaint the JPanel during the while loop in this SA object. 我想在此SA对象的while循环中更新/重新绘制JPanel。 I started a new thread, but still panel.repaint() does not execute. 我启动了一个新线程,但是panel.repaint()仍然无法执行。

public class Mainform extends JFrame {
    private DrawPanel DrawPanel;
    public static void main(String[] args) {
        DrawPanel panel = new DrawPanel();
        SA sa = new SA(panel);
        Thread t = new Thread(sa);
        t.start();
        //...
    }
}
public class DrawPanel extends JPanel implements MouseMotionListener, MouseListener {
    public DrawPanel() {
        super();
        setBackground(Color.WHITE);
        addMouseWheelListener(this);
        addMouseListener(this);
        addMouseMotionListener(this);
    }
    //...
}
public class SA implements Runnable {
    private DrawPanel panel;
    public SA(DrawPanel p) {
        this.panel = p;
        init();
    }
    public void run() {
        while (true) {
            //...
            panel.repaint();
        }
    }
}

EDIT: run is public 编辑:公开运行

The basic answer is "yes". 基本答案是“是”。

This assumes that the component you are trying to repaint is 假设您要重新粉刷的组件是

  1. Added to a container 已添加到容器
  2. That container is attached to some kind of native peer (ie a window) 该容器连接到某种本地对等对象(即窗口)
  3. That window is visible. 该窗口可见。

The RepaintManager is generally smart enough to know not to waste time painting something that isn't displayable. RepaintManager通常足够聪明,以至于不会浪费时间绘画无法显示的内容。

The following example is rather basic, but will increment a counter within the paintComponent of a JPanel each time it is called. 以下示例是非常基本的示例,但是每次调用JPanel时,都会在JPanelpaintComponent中增加一个计数器。 The Runnable , which is attached to a Thread , will update every second... 附加到ThreadRunnable每秒更新一次...

import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class RepaintTest {

    public static void main(String[] args) {
        new RepaintTest();
    }

    public RepaintTest() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                TestPane tp = new TestPane();
                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(tp);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);

                Thread thread = new Thread(new Repainter(tp));
                thread.setDaemon(true);
                thread.start();
            }
        });
    }

    public class Repainter implements Runnable {

        private JPanel panel;

        public Repainter(JPanel panel) {
            this.panel = panel;
        }

        @Override
        public void run() {
            while (true) {
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException ex) {
                }
                panel.repaint();
            }
        }

    }

    public class TestPane extends JPanel {

        private int repaints = 0;

        public TestPane() {
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            Graphics g2d = (Graphics2D) g.create();
            repaints++;
            FontMetrics fm = g2d.getFontMetrics();
            String text = Integer.toString(repaints);
            int x = (getWidth() - fm.stringWidth(text)) / 2;
            int y = ((getHeight() - fm.getHeight()) / 2) + fm.getAscent();
            g2d.drawString(text, x, y);
            g2d.dispose();
        }

    }

}

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

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