2016-06-11 14 views
-1

私は、フレームの中にいくつかのボールが入っていて、側面からはね返るようなフレームを作成するシンプルなクラスを持っています。なんらかの理由で、ボールはフレームの北、西、東の辺から細かくバウンスしますが、バウンスする前に南のサイドをわずかに越えて行きます。私は境界を設定するときにボールのサイズを考慮し、これはx軸でうまく動作しますが、yでは動作しません。アニメーションボールの境界を設定する

import javax.swing.*; 

import java.awt.BorderLayout; 
import java.awt.Color; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.RenderingHints; 
import java.awt.Shape; 
import java.awt.event.*; 
import java.awt.geom.Ellipse2D; 
import java.util.ArrayList; 

public class BallBounceFrame 
{ 

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

JFrame frame; 
static int WIDTH = 500; 
static int HEIGHT = 500; 

public BallBounceFrame() 
{ 
    frame = new JFrame("Ball Bounce Frame"); 
    frame.setSize(WIDTH, HEIGHT); 
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    frame.setLocationRelativeTo(null); 
    frame.setResizable(false); 
    BallCanvas c = new BallCanvas(5); 
    frame.add(c, BorderLayout.CENTER); 
    frame.setVisible(true); 
    c.animate(); 
} 

class BallCanvas extends JPanel 
{ 

    private static final long serialVersionUID = 1L; 

    ArrayList<Ball> balls = new ArrayList<Ball>(); 

    public BallCanvas(int ballNum) 
    { 
     for(int i = 0; i < ballNum; i++) 
     { 
      balls.add(new Ball(20)); 
     } 
    } 

    public void paint(Graphics g) 
    { 
     Graphics2D g2 = (Graphics2D) g; 
     g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); 
     g2.setColor(Color.RED); 
     for(Ball b : balls) 
     { 
      b.move(); 
      g2.fill(b); 
     } 
    } 

    public void animate() 
    { 
     while(true) 
     { 
      try 
      { 
       frame.repaint(); 
       Thread.sleep(10); 
      } 
      catch(Exception e) 
      { 
       System.out.println(e); 
      } 
     } 
    } 
} 

class Ball extends Ellipse2D.Float 
{ 
    private int xVel, yVel; 
    private int size; 
    private int WIDTH = BallBounceFrame.WIDTH; 
    private int HEIGHT = BallBounceFrame.HEIGHT; 

    public Ball(int size) 
    { 
     super((int) (Math.random() * (BallBounceFrame.WIDTH - 20) + 1), (int) (Math.random() * (BallBounceFrame.HEIGHT - 20) + 1), size, size); 
     this.size = size; 
     this.xVel = (int) (Math.random() * 5 + 1); 
     this.yVel = (int) (Math.random() * 5 + 1);   
    } 

    public void move() 
    { 
     if(super.x < 0 || super.x > WIDTH - size) xVel *= -1; 
     if(super.y < 0 || super.y > HEIGHT - size) yVel *= -1; 
     super.x += xVel; 
     super.y += yVel; 
    } 
} 
} 

答えて

0

問題は、WIDTHとHEIGHTがJFrameにあることです。特にウィンドウタイトルのキャプションは、パネルの高さを減少させます。パネルの境界/サイズをボールの移動に渡すことができます。

@Override 
public void paint(Graphics g) 
{ 
    ... 
     b.move(getSize()); 
    ... 
} 

public void move(Dimension panelSize) 
{ 
    if (x < 0 || x > panelSize.getWidth() - size) xVel *= -1; 
    if (y < 0 || y > panelSize.getHeight - size) yVel *= -1; 
    x += xVel; 
    y += yVel; 
} 

あなたは検討するかもしれない範囲内でボールをキープするには:

public void move(Dimension panelSize) 
{ 
    x += xVel; 
    y += yVel; 
    if (x < 0) { 
     x *= -1; 
     xVel *= -1; 
    } else if (x > panelSize.getWidth() - size) { 
     x -= 2 * (x - panelSize.getWidth() - size); 
     xVel *= -1; 
    } 
    if (y < 0) { 
     y *= -1; 
     yVel *= -1; 
    } else if (y > panelSize.getHeight() - size) { 
     y -= 2 * (y - panelSize.getHeight() - size); 
     yVel *= -1; 
    } 
} 

\ |   (xVel == 5) 
    \| 
    /|\ 
    /| \ 
/| \ 

によると、(一つは、通常、レイアウトを行うためにBallBounceFrameの終わりにpack()をCALLA計算)

0

私はその理由がxVel/yVelが動いていると思います。

ボーダーの近くに来たときに、ボーダーを既に通過しているかどうかを確認します。そうでない場合は、ベロシティを追加します。

ボーダーまでの距離が10で、ベロシティが15の場合は、境界フレームに5を移動します。次の動きでは、速度が逆転して跳ね返ります。この場合、移動を分割する必要があります。 10移動、逆方向移動、5移動。

関連する問題