Java 4-Way Pong,坚持检查碰撞

时间:2014-12-07 22:29:42

标签: java user-interface pong collision

我正在制作一个4 Way Pong Program。我知道我的拨片会随着鼠标移动而移动,并且球会在屏幕周围反弹。

在弄清楚如何检查球和球拍之间的碰撞(这将增加得分)以及球与JPanel的边缘之间(将结束比赛)时,我陷入困境。 p>

非常感谢任何指导......

游戏类

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Container;
import java.awt.FlowLayout;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.RandomAccessFile;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.Timer;

public class Game extends JPanel {

    JFrame window = new JFrame();
    Timer timer = new Timer(30, new ActionHandler());
    ArrayList<Ball> balls = new ArrayList<Ball>();
    ArrayList<Paddle> horizPaddles = new ArrayList<Paddle>();
    ArrayList<Paddle> vertPaddles = new ArrayList<Paddle>();
    Paddle pTop;
    Paddle pBottom;
    Paddle pRight;
    Paddle pLeft;
    Ball b;
    int score = 0;
    JLabel scoreLabel;

    //==========================================================
    public Game() {

        window.setBounds(100,100,900,500);
        window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        window.setTitle("4 Way Pong");
        window.setResizable(false);

        JPanel scorePanel = new JPanel(true);

        scoreLabel = new JLabel("Current Score: " + Integer.toString(score));
        scoreLabel.setFont(new Font("sansserif", Font.PLAIN, 20));
        scoreLabel.setForeground(Color.RED);
        scorePanel.add(scoreLabel);

        JPanel buttons = new JPanel(true);

        Container con = window.getContentPane();    
        con.setLayout(new BorderLayout());
        con.add(this, BorderLayout.CENTER);
        con.add(buttons, BorderLayout.SOUTH);
        con.add(scorePanel, BorderLayout.NORTH);

        this.setBackground(Color.BLACK);
        this.addMouseMotionListener(new MouseMoved());

        ButtonCatch bc = new ButtonCatch();

        JButton btn;
        btn = new JButton("New Game");
        btn.addActionListener(bc);
        buttons.add(btn); 

        btn = new JButton("Swap Colors");
        btn.addActionListener(bc);
        buttons.add(btn); 

        btn = new JButton("High Scores");
        btn.addActionListener(bc);
        buttons.add(btn); 

        btn = new JButton("Save Score");
        btn.addActionListener(bc);
        buttons.add(btn); 

        btn = new JButton("Quit");
        btn.addActionListener(bc);
        buttons.add(btn); 

        timer.start();

        window.setVisible(true);
    }

    //==========================================================
    public static void main(String[] args) {             
        new Game();
    }

    //==========================================================
    public void update() {
        for(Ball b : balls) {
            b.move(getWidth() + 30, getHeight() + 25);
        }


        //checkSideCollision();
        //checkHorizPaddleCollision();
        //checkVertPaddleCollision();
        repaint();
    }

    //==========================================================
    public void checkSideCollision() {
        if(b.getyPos() > getHeight()) {
            JOptionPane.showMessageDialog(null, "Game Over.  You Scored " + score + ".", "GAME OVER", JOptionPane.INFORMATION_MESSAGE);
            System.exit(0);
        }
    }

    //==========================================================
    public void checkHorizPaddleCollision() {
        if(b.getxPos() == pBottom.getX() && b.getyPos() == pBottom.getY()) {
            //b.yPos = b.yPos - 5;
            score++;
        }
    }

    //==========================================================
    public void checkVertPaddleCollision() {

    }

    //==========================================================
    public class ButtonCatch implements ActionListener {
        @Override
        public void actionPerformed(ActionEvent e) {
            switch(e.getActionCommand()) {
            case "Quit":        JOptionPane.showMessageDialog(null, "You Quit... No Score Recorded", "Game Over", JOptionPane.INFORMATION_MESSAGE); System.exit(0);
            case "New Game":    newGame(); break;
            case "Swap Colors": swapColors(); break;
            case "High Scores": try { displayScores(); } catch (Exception e1) { System.out.println(e1.getMessage()); } break;
            case "Save Score":   try { saveScore(); } catch (Exception e2) { System.out.println(e2.getMessage()); } break;
            }
        }   
    }

    //==========================================================
    public void paint(Graphics g) {
        super.paint(g);

        for(Ball b : balls) {
            b.draw(g);
        }

        for(Paddle p : horizPaddles) {
            p.draw((Graphics2D) g);
        }

        for(Paddle p : vertPaddles) {
            p.draw((Graphics2D) g);
        }
    }

    //==========================================================
    //FIX FOR DISPLAYING SCORES
    private void displayScores() throws Exception { 

    }

    //==========================================================
    //FIX -- Store Score in a File
    private void saveScore() throws Exception {
        int userScore = score;
        String name = JOptionPane.showInputDialog("Enter Your Name: ");
        JOptionPane.showMessageDialog(null, "Saved!\n" + name + " scored " + userScore, "Score Recorded", JOptionPane.INFORMATION_MESSAGE);
    }

    //==========================================================
    private void swapColors() {
        for(Ball b : balls) {
            if(b.color.equals(Color.red)) { 
                b.setColor(Color.yellow);
            } else if (b.color.equals(Color.yellow)) {
                b.setColor(Color.blue);
            } else {
                b.setColor(Color.red);
            }
        }
    }

    //==========================================================
    private void newGame() {
        //CREATE BALL
        balls.clear();

        b = new Ball();
        b.color = Color.red;
        b.dx = (int)(Math.random() * 4) + 1;
        b.dy = (int)(Math.random() * 4) + 1;
        b.xPos = (int)(Math.random() * 4) + 1;
        b.yPos = (int)(Math.random() * 4) + 1;

        balls.add(b);

        //CREATE PADDLES
        horizPaddles.clear();
        vertPaddles.clear();

            // bottom
        pBottom = new Paddle();
        pBottom.x = getWidth() / 2;
        pBottom.y = getHeight();
        pBottom.setX(pBottom.getX()-20);
        pBottom.setY(pBottom.getY()-20);
        pBottom.setWidth(100);
        pBottom.setHeight(20);
        horizPaddles.add(pBottom);

            //top
        pTop = new Paddle();
        pTop.x = getWidth() / 2;
        pTop.y = getHeight();
        pTop.setX(0 + pTop.getX());
        pTop.setY(0);
        pTop.setWidth(100);
        pTop.setHeight(20);
        horizPaddles.add(pTop);

            //left
        pLeft = new Paddle();
        pLeft.x = getWidth() / 2;
        pLeft.y = getHeight();
        pLeft.setX(0);
        pLeft.setY(pLeft.getY() / 2);
        pLeft.setWidth(20);
        pLeft.setHeight(100);
        vertPaddles.add(pLeft);

            //right
        pRight = new Paddle();
        pRight.x = getWidth() / 2;
        pRight.y = getHeight();
        pRight.setX(875);
        pRight.setY(pRight.getY() / 2);
        pRight.setWidth(20);
        pRight.setHeight(100);
        vertPaddles.add(pRight);

        timer.start();

    }

    //==========================================================
    public class ActionHandler implements ActionListener {

        @Override
        public void actionPerformed(ActionEvent arg0) {
            update();
        }

    }

    //==========================================================
    public class MouseMoved implements MouseMotionListener {

        @Override 
        public void mouseMoved(MouseEvent e) {
            for(Paddle p : horizPaddles) {
                p.x = e.getX();
            }

            for(Paddle p : vertPaddles) {
                p.y = e.getY();
            }
        }

        @Override public void mouseDragged(MouseEvent e) {}

    }

}

划桨类

import java.awt.Color;
import java.awt.Graphics2D;

public class Paddle implements Drawable{
    public int x, y, width, height;

    public Paddle() {
        super();
    }

    public Paddle(int x, int y, int width, int height) {
        super();
        setX(x);
        setY(y);
        setWidth(width);
        setHeight(height);
    }

    @Override
    public void draw(Graphics2D g) {
        g.setColor(Color.green);
        g.fillRect(x, y, width, height);
    }

    public int getX() {
        return x;
    }

    public void setX(int x) {
        this.x = x;
    }

    public int getY() {
        return y;
    }

    public void setY(int y) {
        this.y = y;
    }

    public int getWidth() {
        return width;
    }

    public void setWidth(int width) {
        this.width = width;
    }

    public int getHeight() {
        return height;
    }

    public void setHeight(int height) {
        this.height = height;
    }

}

球类

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Rectangle;
import java.io.IOException;
import java.io.RandomAccessFile;

import javax.swing.JPanel;

public class Ball implements Comparable<Ball>, Cloneable{
    private static int count = 0;
    public static final int NAME_LENGTH = 20;
    public String name = "";
    public int xPos=0, yPos=0, dx = 3, dy = 2;
    public Color color = Color.red;

    public static void resetCounter() { count = 0; }

    public Ball() {name = "Rock: " + ++count;}

    public Ball(RandomAccessFile file) {
        load(file);
    }

    public void load(RandomAccessFile file) {
        try {
            xPos = file.readInt();
            yPos = file.readInt();
            dx = file.readInt();
            dy = file.readInt();
            color = new Color( file.readInt() );

            byte[] n = new byte[NAME_LENGTH];
            file.readFully(n);
            name = new String(n).trim();
            System.out.println(name);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public void save(RandomAccessFile file) {
        try {
            file.writeInt(xPos);
            file.writeInt(yPos);
            file.writeInt(dx);
            file.writeInt(dy);
            file.writeInt(color.getRGB());
            file.writeBytes( getStringBlock(name, NAME_LENGTH) );

        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    private String getStringBlock(String string, int len) {
        StringBuilder sb = new StringBuilder(name);
        sb.setLength(len);
        return sb.toString();       
    }


    public void draw(Graphics g) {
        g.setColor(color);
        g.fillOval(xPos, yPos, 25, 25);
        g.setColor(Color.black);
        g.drawOval(xPos, yPos, 25, 25);
    }

    public void setColor(Color c) {
        color = c;
    }

    public void move(int width, int height) {
        xPos+=dx;
        yPos+=dy;

        if(xPos + 50 > width) {
            xPos = width - 50;
            dx = -dx;
        } 

        if(yPos + 50 > height) {
            yPos = height - 50;
            dy = -dy;
        } 

        if(xPos < 0) {
            xPos = 0;
            dx = -dx;
        }

        if(yPos < 0) {
            yPos = 0;
            dy = -dy;
        }
    }

    @Override
    public int compareTo(Ball arg0) {

        return 0;
    }

    public int getxPos() {
        return xPos;
    }

    public int getyPos() {
        return yPos;
    }

}

再次感谢...

1 个答案:

答案 0 :(得分:0)

对于Paddle-Ball碰撞,我认为在计时器上调用此方法可能就足够了:

 public void checkPaddleCollisions(){
    Rectangle a = new Rectangle(pTop.getX(), pTop.getY(), pTop.getWidth(), pTop.getHeight());
    Rectangle b = ... //Do this for all the paddles.
    Rectangle ball = new Rectangle(ball.getX(), ball.getY(), ball.getWidth(), ball.getHeight());

    if(a.intersects(ball) || b.intersects(ball) || c.intersects(ball) || d.intersects(ball)){
         //Increment score and bounce ball.
    }
}

至于与边缘的碰撞,我认为你可以做类似的事情,只需创建4个代表屏幕边缘的矩形。