[英]JPanel doesn't update until resize Jframe
我子類化JPanel以覆蓋paintComponent(Graphics),我想在jframe中將圖像繪制到jpanel上。
但是直到我更改了jframe的大小,我的圖像才出現。 這是我的代碼:
public class ImagePanel extends JPanel{
public void setImage(BufferedImage bi)
{
image = bi;
revalidate();
}
@Override
public void paintComponent(Graphics g)
{
super.paintComponent(g);
if(image != null)
{
g.drawImage(image, 0, 0, this);
}
}
}
如果要“刷新” JPanel,則應調用repaint(),后者將調用paintComponent()。 這應該可以解決您的問題:
public void setImage(BufferedImage bi)
{
image = bi;
EventQueue.invokeLater(new Runnable()
{
public void run()
{
repaint();
}
});
}
使用EDT更新和更改GUI的良好做法。 如果您有興趣,這里是EDT的更多信息:
不需要從EDT調用repaint
。 如果要更改GUI,例如將文本設置為JLabel,則它應位於EDT內。 以下是有關在EDT之外可以調用的內容的更多信息(由nIcE cOw提供):
看一下JPanel.add()
的文檔 ,它是從java.awt.Container
繼承的:
將指定的組件追加到此容器的末尾。 這是addImpl(java.awt.Component,java.lang.Object,int)的便捷方法。 此方法更改與布局有關的信息,因此使組件層次結構無效。 如果已經顯示了容器,則此后必須驗證層次結構才能顯示添加的組件。
重點已添加。
因此,如果在顯示容器后對其進行修改,則必須調用validate()
使其顯示。 僅調用repaint()
是不夠的。 您可能已經注意到,調用setVisible(true)
也可以; 這是因為它在內部調用validate()
。
我有同樣的問題,可以通過調用setVisible(true)來解決。 我正在使用的JFrame。
示例:如果您的JFrame在使用后沒有更新:
jframe.setContentPane(new MyContentPane());
修復:
jframe.setContentPane(new MyContentPane());
jframe.setVisible(true);
我知道即使您的JFrame已經可見,執行此操作聽起來也很愚蠢,但這是我到目前為止找到的解決此問題的唯一方法(上面提出的解決方案對我不起作用)。
這是一個完整的例子。 運行它,然后取消注釋“ f.setVisible(true);” 類Panel1和Panel2中的說明,您將看到區別。 不要忘記導入(對於自動導入,請按Ctrl + Shift + O)。
主類:
public class Main {
private static JFrame f;
public static void main(String[] args) {
f = new JFrame();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setContentPane(new Panel1(f));
f.pack();
f.setVisible(true);
}
}
Panel1類:
public class Panel1 extends JPanel{
private JFrame f;
public Panel1(JFrame frame) {
f = frame;
this.setLayout(new BoxLayout(this, BoxLayout.LINE_AXIS));
JButton b = new JButton("Panel 1");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
f.setContentPane(new Panel2(f));
// Uncomment the instruction below to fix GUI "update-on-resize-only" problem
//f.setVisible(true);
}
});
add(b);
}
}
Panel2類:
public class Panel2 extends JPanel{
private JFrame f;
public Panel2(JFrame frame) {
f = frame;
this.setLayout(new BoxLayout(this, BoxLayout.LINE_AXIS));
JButton b = new JButton("Panel 2");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
f.setContentPane(new Panel1(f));
// Uncomment the instruction below to fix GUI "update-on-resize-only" problem
//f.setVisible(true);
}
});
add(b);
}
}
希望能有所幫助。
問候。
我也有同樣的問題,但我找到了解決方案。 只需在頂部創建一個jframe
對象,然后在底部調用jframe
方法,例如jf.pack()
, jf.setVisible()
, jf.setSize()
, jf.setDefaultCloseOpetion()
應該位於添加的所有UI的底部框架,您會發現它很棒。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.