2013-08-03 99 views
0

基本目標是讓一個JPanel以3x3模式填充9個白色方塊;正方形是150x150空白的白色.jpg文件。它必須是這種方式,因爲以後,程序必須將空白方塊更改爲一系列簡單圖像之一,並且必須能夠隨時更改任何方塊。 問題是,我得到一個NullPointerException。我不得不認爲這與將數組初始化爲空有關,但如果我不這樣做,NetBeans(是的,NetBeans ...)似乎會生我的氣。如果我嘗試聲明數組的大小,則相同。 (這將是...... 「數組類型[ARRAYSIZE] arrayName中;」?,是」Java - 使用ImageIcons通過循環(NullPointerException)填充一個JLabel數組

EGH,我只是猜測瘋狂

編輯 - NullPointerException異常固定,但現在空(白)圖片。簡單地沒有出現在框架的下方編輯代碼以反映其新的狀態,更可能相關的行添加

這裏是所有相關的代碼:

JFrame controller = new JFrame("SmartHome Interface"); 
controller.setVisible(true); 
controller.setSize(480,500); 
controller.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

//[...] 

JPanel labelPanel = new JPanel(); 

//[...] 

labelPanel.setBackground(Color.GREEN); 

//[...] 

ImageIcon blank = new ImageIcon("../Images/blank.jpg"); 

//[...] 

controller.add(labelPanel); 

//[...] 

JLabel[] labels = new JLabel[9]; 
     for (int i = 0; i <= 8; i++) 
     { 
      int xLowBound; 
      int xUpBound; 
      int yLowBound; 
      int yUpBound; 

      //Maths for positioning the labels correctly. Should be 150px in size with 10px gaps each. 
      xLowBound = (i % 3) * 160; 
      xUpBound = xLowBound + 150; 
      yLowBound = (i/3) * 160; 
      yUpBound = yLowBound + 150; 

      labels[i] = new JLabel(); 
      labels[i].setIcon(blank); 
      labels[i].setBounds(xLowBound, yLowBound, xUpBound, yUpBound); 
      labelPanel.add(labels[i]); 
     } 

另外.....是文件路徑爲ImageIcon正確? 代碼本身位於「src/smarthome」和「src/Images」中的圖像

如果我違反了任何論壇公約/行爲準則/等,請致歉。紐比在這裏,試圖小心不要,但我可能已經忘記了一些東西。

回答

2

你的問題簡化爲如下:

JLabel[] labels = null; 
for (int i = 0; i <= 8; i++) { 
    labels[i].setIcon(blank); 
} 

這段代碼將失敗,因爲標籤== NULL。因此標籤[i] == null。

使用這個代替:

JLabel[] labels = new JLabel[9]; 
for (int i = 0; i <= 8; i++) { 
    labels[i] = new JLabel(); 
    labels[i].setIcon(blank); 
} 
+0

謝謝,我照你說的,這正是做,我不再收到錯誤,但是空(白)圖像只未出現在框架上。 – Malix

2

您的imageIcons文件路徑不正確。您應該使用:

ImageIcon img = new ImageIcon(getClass().getResource("../Images/blank.jpg"));  

如果你的代碼是在靜態方法使用這樣的:

ImageIcon img = new ImageIcon(YourClass.class.getResource("../Images/blank.jpg")); 

有關於加載圖像圖標的好answer(感謝尼斯牛)。


你應該將所有組件添加到幀後調用setVisible()setSize()


將組件添加到幀的內容窗格(frame.getContentPane())。


你總是應該把你的GUI代碼放在單獨的線程中。


所以,你的代碼將是:

SwingUtilities.invokeLater(new Runnable() 
{ 

    @Override 
    public void run() 
    { 
     JFrame controller = new JFrame("SmartHome Interface"); 
     controller.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

     JPanel labelPanel = new JPanel(); 

     labelPanel.setBackground(Color.GREEN); 

     // !!! 
     ImageIcon blank = new ImageIcon(YourClass.class 
       .getResource("../Images/blank.jpg")); 

     // !!! 
     controller.getContentPane().add(labelPanel); 

     JLabel[] labels = new JLabel[9]; 
     for (int i = 0; i <= 8; i++) 
     { 
      int xLowBound; 
      int xUpBound; 
      int yLowBound; 
      int yUpBound; 

      xLowBound = (i % 3) * 160; 
      xUpBound = xLowBound + 150; 
      yLowBound = (i/3) * 160; 
      yUpBound = yLowBound + 150; 

      labels[i] = new JLabel(); 
      labels[i].setIcon(blank); 
      labels[i].setBounds(xLowBound, yLowBound, xUpBound, 
        yUpBound); 
      labelPanel.add(labels[i]); 
     } 

     // !!!  
     controller.setVisible(true); 
     controller.setSize(480, 500); 

    } 
}); 
+0

請不要在同一個線程上發佈多個答案,而是編輯這個包含其他兩個答案。這樣你就不會失去這些你已經獲得的積分。儘管GUI在EDT上啓動,但在將所有組件添加到容器之後仍然會調用像「pack()/ setVisible()」,而不是在此之前。以前這樣做會給人厭惡的結果:-) –

+0

你是對的=) – Barataliba

+0

這裏是我的+1,雖然關於路徑thingy,請參考這個[答](http://stackoverflow.com/a/9866659/1057230 ):-) –