[英]Adding Panel from Another Class to Main Class
我正在嘗試將單獨的 class 中的 JPanel 和 JButton 添加到框架中,該框架位於主 class 中。 程序編譯沒有錯誤,但只顯示黑色 window。 視覺目標是讓按鈕在單擊時改變顏色。 我在 GUI_1_1 class 中創建按鈕,並在主 class 中創建框架。 我究竟做錯了什么?
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.*;
public class main {
public static void main(String[] args) {
JFrame frame = new JFrame ("Cube GUI");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setResizable(false);
frame.setSize(1370,790);
frame.getContentPane().setBackground(Color.BLACK);
frame.add(new GUI_1_1());
frame.setVisible(true);
}
}
下面是第二個 class
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.*;
public class GUI_1_1 extends JPanel {
private int count;
private JButton button0;
private JPanel mainpanel;
private JPanel panel1;
public GUI_1_1() {
mainpanel = new JPanel();
mainpanel.setLayout(null);
count = 0;
button0 = new JButton("[1][1]");
button0.addActionListener(new ButtonListener());
button0.setOpaque(true);
button0.setBounds(60,310,50,50);
mainpanel.add(button0);
add(mainpanel);
}
private class ButtonListener implements ActionListener {
@Override
public void actionPerformed(ActionEvent event) {
if(count==0){
button0.setBackground(Color.RED);
count = count + 1;
} else if(count==1) {
button0.setBackground(Color.GREEN);
count = count + 1;
} else if(count==2) {
button0.setBackground(Color.ORANGE);
count = count + 1;
} else if(count==3) {
button0.setBackground(Color.BLUE);
count = count + 1;
} else if(count==4) {
button0.setBackground(Color.YELLOW);
count = count + 1;
} else if(count==5) {
button0.setBackground(Color.WHITE);
count = count - 5;
}
}
}
}
好的,這里有很多東西要解釋你做錯了什么,所以我無法為你分解它。 不過,我可以從基礎開始。
不要太用力。 Swing 是它自己的東西。 Java 以非常抽象而著稱,因此您不必知道它是如何工作的 - just call it and let Java figure it out for you
。 對於 Java,我並不完全同意,但對於 Swing,我絕對不同意。 Swing 正是因為這個原因而聲名狼藉,我認為 90% 的時間都是沒有根據的。
僅僅因為你調用一個抽象的 API 並不意味着你不必知道它是如何工作的。 Swing 尤其是這種方式。 也就是說,我什至無法在這個答案中開始分解它,因為有很多細節,其中很多甚至不直接適用於你的代碼,但你應該間接知道,所以你只需要花費時間學習它只需要時間和閱讀。 不過,最重要的是,Swing 不僅僅是一些你不必理解的抽象黑盒——你必須學習它,而不僅僅是調用隨機函數,否則你最終會發現你的代碼行為不端.
你可能會覺得這很煩人(與你的問題無關),但在你完成學習后它變得很重要 - 處理你的 class 命名。 類應該對它們所做的事情進行自我描述,因此盡管 JavaDocs 很有幫助,但對於閱讀您的代碼的人來說,它們不應該是 100% 必要的,以了解它在做什么。
最后回答你的問題。
切勿在事件調度線程 (EDT) 之外進行 GUI 工作。 在任何具有 GUI 的環境中,您都有一個單獨的線程來完成該顯示工作。 您的音樂播放器擁有它,您的互聯網瀏覽器可以處理它 - Java 也不例外。 並且要真正把它帶回家,這是多么重要 - 如果您能弄清楚如何進行多線程 GUI 工作,那么您就可以賺很多錢,並且再也不會為您一生中的 rest 工作。
您的 main 方法在它自己的線程中運行,並且 EDT 由您的程序隱式啟動。 您的 GUI 應該在 EDT 中更新,而我之前提到的 Java(和 Swing)所做的那些抽象的事情,將在 EDT 中自動發生。 但是,您的代碼沒有。 你想看的是SwingUtilities.html#invokeLater(java.lang.Runnable) (或者invokeAndWait(...) )你把你的代碼作為
public static void main (String [] args) {
SwingUtilities.invokeLater(()->{
//things you want to happen only in the EDT
});
//other things to happen in your main thread
然后就是你說的那一行:
frame.add(new GUI_1_1());
所以JFrame
與其他容器略有不同。 您不想將東西“添加”到JFrame
。 相反,您希望將JPanel
設置為JFrame
的內容窗格。
除此之外,您獲取內容窗格之前的行,然后設置它的背景顏色。 其中,現在您將使用GUI_1_1
作為內容窗格,您可以想象該行將不再有意義。 順便說一句,就您聲稱看到的黑屏而言,您的內容窗格不是您的顯示器似乎是問題所在。
您在GUI_1_1
的構造函數中所做的一件事是將布局管理器設置為 null。 這是它自己的另一件事,我不會真正詳細說明,因為它的類型太多 - 而 Oracle 已經做得很好,我完全建議閱讀以了解如何正確使用布局管理器: https ://docs.oracle.com/javase/tutorial/uiswing/layout/visual.html
我可以繼續討論一段時間,但這個答案已經很冗長了。 就像我提到的,Swing 是一個完整的東西,只需要學習它,就像任何 API 一樣。
如果您有其他問題或其他細節,我可以繼續編輯此答案並提供更多信息或指向更多閱讀的鏈接。 但我將縮短這一點,以保留更多“通用”建議,這些建議來自我上面已經提出的建議。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.