2012-03-17 105 views
-1

我一直在研究一個可以在其上玩Pong的程序,而且我對多線程相對比較陌生。當我運行這個代碼塊時,它應該在左上角顯示一個小盒子,其中一個球彈跳在一個盒子中,一個大矩形在中心。球來了,但矩形沒有。Java多線程 - 跳過代碼行?

private void gameRender() { 

    if(dbImage == null) { 
     dbImage = createImage(dbWIDTH, dbHEIGHT); 
     if(dbImage == null) { 
      JOptionPane.showMessageDialog(null, "dbImage is null", "Error",     JOptionPane.ERROR_MESSAGE); 
      return; 
     } 
     else 
      dbg = dbImage.getGraphics(); 
    } 

    dbg.setColor(Color.white); 
    dbg.fillRect(100, 150, dbWIDTH, dbHEIGHT); 
    dbg.setColor(Color.blue); 
    dbg.drawRect(110, 110, 10, 5); 
    g = getGraphics(); 
    ball = new PongBall(g); 
    ball.run(); 
    if(gameOver) 
     JOptionPane.showMessageDialog(null, "GAME OVER", "GAME OVER", JOptionPane.ERROR_MESSAGE); 
} 

這裏的PongBall線程

class PongBall extends Thread { 

private boolean keepGoing; 
private Graphics g; 
private int x = 7, xChange = 7; 
private int y = 0, yChange = 2; 
private int diameter = 10; 
private int rectLeftX = 0, rectRightX = 100; 
private int rectTopY = 0, rectBottomY = 100; 

public PongBall(Graphics graphics) { 
    g = graphics; 
    keepGoing = true; 
} 

public void pleaseStop() { keepGoing = false; } 

public void run() { 


    g.drawRect(rectLeftX, rectTopY, rectRightX - rectLeftX, rectBottomY - rectTopY); 

    while(keepGoing) { 

     g.setColor(Color.white); 
     g.fillOval(x, y, diameter, diameter); 

     if(x + xChange <= rectLeftX) 
      xChange = -xChange; 
     if(x + xChange >= rectRightX) 
      xChange = -xChange; 

     if(y + yChange <= rectTopY) 
      yChange = -yChange; 
     if(y + yChange >= rectBottomY) 
      yChange = -yChange; 

     x = x + xChange; 
     y = y + yChange; 

     g.setColor(Color.red); 
     g.fillOval(x, y, diameter, diameter); 

     try { 
      Thread.sleep(50); 
     } 
     catch(InterruptedException e) { 
      System.err.println("sleep exception"); 
     } 
    } 
} 

} 正如你很可能會看到, 「dbg.fillRect(100,150,dbWIDTH,dbHEIGHT);」被跳過並且ball.run()運行。有沒有我不做的事情,我該如何解決這個問題?

此外,我是新的stackoverflow.com,所以如果我給了太多或太少的代碼,或任何錯誤,我很抱歉。

+0

這實際上並不涉及多個線程,因爲您只是在您的'PongBall'上調用'run()',而不是調用'start()'。 (請注意,這可能是一件好事,因爲更新UI應該發生在單個線程上。)我認爲你的問題是你只是創建一個圖像,但實際上並沒有渲染到屏幕上。 – dlev 2012-03-17 18:38:22

+0

我會將它渲染到屏幕上。我在測試代碼時排除了「ball.run()」代碼行,並且矩形顯示出來了,但是使用該代碼行則沒有。但是謝謝你的提示,一個線程應該更新UI – kullalok 2012-03-17 18:51:01

+0

很難說,但我認爲你的球正在畫在矩形上並擦除它。使用調試器來查看發生了什麼,因爲現在你只有一個線程。 – 2012-03-17 18:52:17

回答

0

我建議你在Swing線程中做所有的繪圖。你可以在你的PongBall線程中使用SwingUtilities.invokeLater來包含所有更新GUI的代碼。

這可以避免GUI中的任何多線程問題,因爲只有一個線程用於更新顯示。

0

我認爲你犯了兩個錯誤。 首先,你應該調用方法「start()」來啓動一個線程而不是「run()」。其次,如何歸檔Swing組件的圖形對象?不要使用「getGraphics()」方法,它不起作用。你應該重寫方法paintComponent(Graphics g)。

+0

爲我的答案的第二點表示歉意,因爲你讓一個線程循環繪製,效果很好。 – 2012-03-17 19:20:25

+0

不,它不會很好。 – 2012-03-17 19:36:07