2013-05-19 57 views
1

我有兩個使用java swing的遊戲板的按鈕監聽器。Java Swing Button聽衆不工作

最初創建了一個俄羅斯方塊網格,然後在每個按鈕偵聽器中添加了功能。

我設置的板像這樣在我Play.java:

final TetrisGame g = new TetrisGame(11,1); 
final BoardGraphics graphics = new BoardGraphics(TetrisBoard.BOARD_WIDTH, 40, g); 

按鈕偵聽器,然後在同一Play.java創建:

graphics.btnStart.addActionListener(new ActionListener() 
     { 
      public void actionPerformed(ActionEvent e) 
      { 
       Action arc = p.getAction(g); 
       g.update(arc); 
       graphics.colours.clear(); 
       graphics.setColor(g.getBoard().getGrid()); 
       while (arc instanceof Store){ 
        arc = p.getAction(g); 
        g.update(arc); 
        graphics.colours.clear(); 
        graphics.setColor(g.getBoard().getGrid()); 
       } 

      graphics.tiles.redraw(); 
      System.out.println(); 
      System.out.println(g.toString()); 
      System.out.println(); 
      } 

     }); 


     graphics.btnAuto.addActionListener(new ActionListener() 
     { 
      public void actionPerformed(ActionEvent e) 
      { 

       while (!g.gameEnded()){ 
        Action arc = p.getAction(g); 
        g.update(arc); 
        graphics.colours.clear(); 
        graphics.setColor(g.getBoard().getGrid()); 
        while (arc instanceof Store){ 
         arc = p.getAction(g); 
         g.update(arc); 
         //graphics.colours.clear(); 
         graphics.setColor(g.getBoard().getGrid()); 
        } 
        graphics.tiles.redraw(); 
        System.out.println(); 
        System.out.println(g.toString()); 
        System.out.println(); 
        /*try { 
        Thread.sleep(1000); 
       } catch (InterruptedException e1) { 
        // TODO Auto-generated catch block 
        e1.printStackTrace(); 
       }*/ 

       } 

      } 

     }); 

的btnStart完美的作品,按有一次,根據人工智能代理給出的下一步行動繪製了tetrisboard。

我希望btnAuto可以在沒有用戶按btnStart的情況下播放每一個動作直到結束。不過,我的btnAuto並沒有在網格上繪製任何東西,而是繪製了遊戲的最終狀態,即完成狀態。

任何人都可以看到爲什麼這可能不會重新繪製每個移動後,在while循環中生成網格嗎?

回答

3

while循環被稱爲Swing事件線程上,並因此防止從做必要的操作,包括渲染圖形用戶界面和與用戶交互的線程:

while (!g.gameEnded()){ 
    Action arc = p.getAction(g); 

    // .... 

} 

我會用一個Swing Timer這裏而不是while (true)循環。另一種選擇是使用後臺線程,但由於你所需要的只是一個非常簡單的遊戲循環,並且不需要在後臺運行一些長時間運行,我認爲這第二種選擇會更復雜,沒有額外的好處。另外,我很好奇你是如何做你的繪圖以及如何讓你的Graphics對象繪製的。你不打電話給getGraphics()組件,是嗎?


編輯您在留言註明:

我現在有與擴展JPanel嵌套類的類。電網和的getGraphics()的繪圖嵌套class.The父類中完成創建組件,並設置了GUI的整體佈局

不要通過主叫getGraphics()得到一個圖形對象作爲Graphics對象獲得的GUI組件不會持久。要看到這一點,只需最小化,然後恢復您的應用程序,並告訴我在完成此操作後圖形會發生什麼。您應該在JPanel的paintComponent重寫中完成所有繪圖。一種選擇是在BufferedImage上調用getGraphics()並使用它繪製到BufferedImage,然後在paintComponent重寫中顯示BufferedImage。如果使用第二種技術,在完成使用後不要忘記處理BufferedImage的Graphics對象,以免佔用系統資源。

+0

這工作完美..也解決了我在沒有把我的應用程序進入睡眠狀態時在while循環中使用計時器的問題。 –

+0

@DizzyChamp:很高興幫助! –

+0

我目前有一個擴展了JPanel的嵌套類。網格和getGraphics()的繪圖是在嵌套類中完成的。父類創建組件並將GUI的佈局設置爲一個整體。 –