2014-01-17 62 views
0

我已经在Java中创建了弹跳球应用程序。目标是在mousePressed()上出现一个球,并在不离开框架的情况下将其弹出墙壁。只有一个球一个线程,应该很容易.. 我的问题是,每次我点击使球出现,它会变得更快,我不知道为什么。有人可以帮助我。 PS:我是新来的线程。Java简单弹跳球,单线程,鼠标监听器,JFrame

import java.awt.Graphics; 
import java.awt.event.MouseEvent; 
import java.awt.event.MouseListener; 
import javax.swing.JFrame; 
import javax.swing.JPanel; 

public class MyFrame extends JPanel { 
public int xPos, yPos, xDir = 3, yDir = 4; 
public int diameter = 50; 

public MyFrame(){ 
    final JFrame thisFrame = new JFrame(); 
    thisFrame.add(this); 
    thisFrame.setTitle("Bouncing Ball"); 
    thisFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    thisFrame.setLocationRelativeTo(null); 
    thisFrame.setSize(500, 500); 

    this.addMouseListener(new MouseListener() { 
     @Override 
     public void mouseReleased(MouseEvent e) {} 
     @Override 
     public void mousePressed(MouseEvent e) { 
      xPos = e.getX(); 
      yPos = e.getY(); 
      Thread t = new Thread() { 
       @Override 
       public void run() { 
        while(true){ 
         try{ 
          Thread.sleep(10); 
         }catch(Exception e){}; 
         xPos += xDir; 
         yPos += yDir; 

         if(xPos + diameter >= thisFrame.getWidth() - 25 || xPos <= 0) xDir = -xDir; 
         if(yPos + diameter >= thisFrame.getHeight() - diameter || yPos <= 0) yDir = -yDir; 
         repaint(); 
        } 
       } 
      }; 
      t.start(); 
     } 
     @Override 
     public void mouseExited(MouseEvent e) {} 
     @Override 
     public void mouseEntered(MouseEvent e) {} 
     @Override 
     public void mouseClicked(MouseEvent e) {} 
     }); 

    thisFrame.setVisible(true); 

    } 
    public void paintComponent(Graphics g) { 
     super.paintComponent(g); 
     g.fillOval(xPos, yPos, diameter, diameter); 
    } 
} 
public class MyMain{ 

    public static void main(String[] args) { 
     new MyFrame(); 
    } 

} 
+0

当你不需要重写每个鼠标事件方法时,使用'MouseAdapter'。 –

回答

1

每当你点击,你开始一个新的线程,这意味着你有另一个线程更新X/Y位置。例如,1个线程表示您每次更新x/p一次,2表示您正在更新x/y位置至少每个周期两次,并且每次添加新线程时都会复杂化。

更好的解决方案是在较早的某个时间启动Thread,然后使用List来保持球的位置和方向。

这需要一点点,但同步保平安

FYI 40毫秒的延迟大约是每秒25帧,16毫秒是大约60 FPS。恕我直言,你在做什么,10毫秒似乎过分...

+0

如果我理解正确,每次点击,前一个线程都不会死。导致多个线程...?对不起,如果我有点困惑。你是说我应该在鼠标按下的时候初始化线程并在鼠标按下的时候启动它?如果是这种情况,在再次启动之前我不必终止它?谢谢你的帮助。 – Matz0rz

+0

对第一部分是肯定的。第二部分将取决于你想要做什么。如果你只想要一个球,那么。您可以简单地重置x/y位置,而不用担心其他事情。如果你想要更多球,那么你需要使用某种列表来维护管理每个球所需的信息 – MadProgrammer

+0

我还应该指出,javax.swing.Timer会更容易管理,并且从更新点更安全的视图 – MadProgrammer