0
\$\begingroup\$

How do I make my ball bounce off objects on the screen? I'm having trouble detecting the collision, as well as calculating the response.

The picture below is a good example of how the program should be working once the ball runs into an obstacle

enter image description here

I made the ball bounce off the walls, but what's left is making it also bounce off of objects. Thanks for the help!

Here's the source code:

public class 2DGAME extends Application {

    public static Circle circle;
    public static Pane canvas;
    private long counter = 0;
    double X = 0;
    double Y = 0;

    @Override
    public void start(Stage primaryStage) {

        canvas = new Pane();
        Scene scene = new Scene(canvas, 800, 600);

        primaryStage.setTitle("2D Ball Game");
        primaryStage.setScene(scene);
        primaryStage.show();

        circle = new Circle(20, Color.BLUE);
        circle.relocate(100, 100);

        final Rectangle r = new Rectangle(20, 20, Color.DARKMAGENTA);
        r.setLayoutX(400);
        r.setLayoutY(300);

        canvas.getChildren().addAll(circle);
        canvas.getChildren().addAll(r);


        Timeline loop = new Timeline(new KeyFrame(Duration.millis(5), new EventHandler<ActionEvent>() {

            @Override
            public void handle(ActionEvent t) {
                if (counter++ % 5 == 0) {
                    // Moves the ball depending on the values of X and Y
                    circle.setLayoutX(circle.getLayoutX() + X);
                    circle.setLayoutY(circle.getLayoutY() + Y);

//Code to bounce off walls
                    final Bounds bounds = canvas.getBoundsInLocal();
                    boolean leftWall = circle.getLayoutX() <= (bounds.getMinX() + circle.getRadius());
                    boolean topWall = circle.getLayoutY() <= (bounds.getMinY() + circle.getRadius());
                    boolean rightWall = circle.getLayoutX() >= (bounds.getMaxX() - circle.getRadius());
                    boolean bottomWall = circle.getLayoutY() >= (bounds.getMaxY() - circle.getRadius());

   //Bugged and not sure how to make it work
                    final Bounds rectangleBounds = r.getLayoutBounds();
                    boolean rectangle_left = circle.getLayoutX() <= (rectangleBounds.getMinX() + circle.getRadius());
                    boolean rectangle_right = circle.getLayoutX() >= (rectangleBounds.getMaxX() - circle.getRadius());


   //If the bottom or top wall has been touched, the ball reverses direction.
                    if (bottomWall || topWall) {

                        Y = Y * -1; 
                    }
    // If the left or right wall has been touched, the ball reverses direction.
                    if (leftWall || rightWall) {
                        X = X * -1;
                    }

    //Bugged code for boucning off obstacle object
                    if (rectangle_left || rectangle_right) {
                       // X = X * - 1;
                    }

                }
            }

        }));

        loop.setCycleCount(Timeline.INDEFINITE);
        loop.play();
    }

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

}
\$\endgroup\$
  • 1
    \$\begingroup\$ What's the different between walls and any other object? Please try to be more specific about what your problem is. Are you having trouble detecting the collision? Calculating the response? \$\endgroup\$ – MichaelHouse Nov 18 '13 at 15:04
  • \$\begingroup\$ I am having trouble with both, I clarified it in the main question now. \$\endgroup\$ – Gregg1989 Nov 18 '13 at 16:27
  • 1
    \$\begingroup\$ Thanks. Can you now explain what's not working about each? How to detect collisions and how to respond to them are both very broad questions. If you tell us how you want it to work and what you've tried already (and exactly what about it isn't working) you're more likely to get the help you need. \$\endgroup\$ – MichaelHouse Nov 18 '13 at 17:01
  • 1
    \$\begingroup\$ @user2915567 Telling us exactly what you tried for the wall detection and what you have in mind for the "other" objects can greatly help. Since In "normal" circumstances there shouldn't be any difference in both cases, so maybe you are asking the wrong question. \$\endgroup\$ – concept3d Nov 18 '13 at 17:16
  • \$\begingroup\$ if you have any knowledge on vectors ( direction, magnitude ) you need to reflect against an axis ( that is if you're using simple rectangles as obstacles) \$\endgroup\$ – Sidar Nov 18 '13 at 19:44
4
\$\begingroup\$

Just use the same bounds checking you do with your walls but this time apply it to your object.

For each update :

  • Check where the ball is
  • Check where the object is
  • Check if they collide
  • Check from what angle is the collision
  • Bounce your ball like with your walls

If there are multiple objects (and I mean like hundreds) you might want to narrow down your collision checking so that you don't check unnecessary objects.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.