|
Pong Collision |
Luna Wu
Member #16,273
April 2016
|
1int x = 1; #include <stdio.h>
2#include <allegro5/allegro.h>
3#include "allegro5/allegro.h"
4#include "allegro5/allegro_image.h"
5#include <allegro5/allegro_native_dialog.h>
6#include <allegro5/allegro_primitives.h>
7#include <allegro5/color.h>
8#include <allegro5/allegro_color.h>
9#include <allegro5/allegro5.h>
10#include <allegro5/color.h>
11#include <allegro5/allegro_font.h>
12#include <allegro5/allegro_ttf.h>
13#include <iostream>
14
15ALLEGRO_EVENT ev;
16int main(){
17 int d = 200;
18 int f = 200;
19 int x = 700;
20 int y = 100;
21 int a = 100;
22 int b = 100;
23 int ballx = 200;
24 int bally = 200;
25 int ballXSpeed = 5;
26 int ballYSpeed = 3;
27 bool ballmoving = true;
28 al_init_image_addon();
29 ALLEGRO_BITMAP *Player1;
30 ALLEGRO_BITMAP *Player2;
31 ALLEGRO_BITMAP *ball;
32 ALLEGRO_DISPLAY *display = NULL;
33
34 ALLEGRO_EVENT_QUEUE *eventqueue = NULL;
35 ALLEGRO_TIMER *timer = NULL;
36
37 bool playing = true;
38 al_init();
39 al_init_primitives_addon();
40 display = al_create_display(800, 600);
41 al_install_keyboard();
42 eventqueue = al_create_event_queue();
43 timer = al_create_timer(1.0 / 60.0);
44 al_register_event_source(eventqueue, al_get_keyboard_event_source());
45 al_register_event_source(eventqueue, al_get_display_event_source(display));
46 al_register_event_source(eventqueue, al_get_timer_event_source(timer));
47 Player1 = al_load_bitmap("brick.png");
48 Player2 = al_load_bitmap("brick.png");
49 int P1W = al_get_bitmap_width(Player1);
50 int P1H = al_get_bitmap_height(Player1);
51 int P2W = al_get_bitmap_width(Player2);
52 int P2H = al_get_bitmap_height(Player2);
53 ball = al_load_bitmap("ball.png");
54
55 while (playing){
56
57
58 al_clear_to_color(al_map_rgb(255, 255, 0));
59 al_wait_for_event(eventqueue, &ev);
60 al_start_timer(timer);
61 if (ev.type == ALLEGRO_EVENT_TIMER){
62
63 ballx = ballx + ballXSpeed;
64 bally = bally + ballYSpeed;
65 if (ballx < x+P1W && ballx>x-P1W &&bally<y+P1H && bally>y){
66 ballXSpeed = ballXSpeed * -1;
67 ballYSpeed = ballYSpeed*-1;
68 }
69 if (ballx > a + P2W && ballx < a+P2W+10 && bally <b + P2H &&bally>b){
70 ballXSpeed = ballXSpeed*-1;
71 ballYSpeed = ballYSpeed*-1;
72 }
73 if (ballx > 800 || bally > 600){
74 ballx = 400;
75 bally = 400;
76 std::cout << "2 wins!" << std::endl;
77 }
78 if (ballx<-1 || bally<-1){
79 ballx = 400;
80 bally = 400;
81 std::cout << "1 wins!" << std::endl;
82 }
83 }
84 if (ev.type = ALLEGRO_EVENT_KEY_DOWN){
85 switch (ev.keyboard.keycode){
86 case ALLEGRO_KEY_UP:
87 y -= 20;
88 break;
89 case ALLEGRO_KEY_DOWN:
90 y += 20;
91 break;
92 case ALLEGRO_KEY_W:
93 b -= 20;
94 break;
95 case ALLEGRO_KEY_S:
96 b += 20;
97 break;
98
99
100 }
101 }
102
103 al_draw_bitmap(Player1, x, y, 0);
104 al_draw_bitmap(Player2, a, b, 0);
105 al_draw_bitmap(ball, ballx, bally, 0);
106 al_flip_display();
107 }
108
109 al_flip_display();
110 al_rest(5);
111}
Hey guys, I'm making a pong game, but I've been stuck in the collision thing for a while now, the problem is when the paddles (bricks) are in a place up, the collision isn't detected and the ball passes right through them, but when they're down, it is detected and the ball bounces off. Could anyone please help? |
Niunio
Member #1,975
March 2002
|
First of all: Put all your code inside the main function is a VERY BAD idea. You're not coding in BASIC nor Assemble (and even in that languages you can structure your code). Create a few structs (paddle, ball, brick...) and split code in functions and even in different modules (ball.c, play.c, title.c...). See the example code included with Allegro. Just doing that may be you find what's wrong with your code by your own. ----------------- |
Audric
Member #907
January 2001
|
I don't really understand the collision code, but it looks suspicious : |
Neil Roy
Member #2,229
April 2002
|
I created a quick pong game a couple years ago, and my collision function (you really should separate your code into functions) basically went like this... if(bottom1 < top2) return 0; if(top1 > bottom2) return 0; if(right1 < left2) return 0; if(left1 > right2) return 0; It gets the bottom, top, left and right side (bounding box) of each object to test, then it does the above checks. if the bottom of one is higher up on the screen than the top of the other, than they are obviously not colliding. The same for the left and right sides, if the right side of one object is less than the left side of the other, than they cannot be colliding. This is better than checking to see if they overlap. If all four of the above checks fail, than you have a collision, you can then report a collision, or do further checks if you wish to have pixel perfect collision. Another method for collision detection which is easy, is circular. You basically assign a radius to each object for collision, you then check the distance between the two objects using some simple math, and if the distance is less than the sum of the two radiuses, than you have a collision. Otherwise you do not. It's probably one of the easiest to do. --- |
duncan perham
Member #15,403
November 2013
|
Write a function like bool IsRectInRect(RECT *Paddle,RECT *Ball, long Offset) |
Peter Hull
Member #1,136
March 2001
|
Hi Luna, I love Pong; I used to have one of those things you plug into the TV!* I would say:
I didn't fully understand what you said was wrong with it but at the moment Player 1 wins if the ball hits the top and Player 2 wins if it hits the bottom. Also the ball bounces in an unusual way, as Audric says. In your collision code you need to take the size of the ball into account. I would do something like this: [ ball size is (BW, BH) ] 1 // Check hit bat 1
2 if (ballx < x + P1W && ballx + BW >= x && bally + BH >= y && bally < y + P1H) {
3 if (ballXSpeed > 0) {
4 ballXSpeed = -ballXSpeed;
5 }
6 }
7 // Check hit bat 2
8 if (ballx < a + P2W && ballx + BW >= a && bally + BH >= b && bally < b + P2H) {
9 if (ballXSpeed < 0) {
10 ballXSpeed = -ballXSpeed;
11 }
12 }
13 // Check going off RHS
14 if (ballx >= 800) {
15 ballx = 400;
16 bally = 300;
17 std::cout << "2 wins!" << std::endl;
18 }
19 // Check going off LHS
20 if (ballx < 0) {
21 ballx = 400;
22 bally = 300;
23 std::cout << "1 wins!" << std::endl;
24 }
25 // Check top and bottom
26 if (bally < 0 || bally + BH >= 600) {
27 ballYSpeed = -ballYSpeed;
28 }
The bouncing is still not right though, IIRC in pong you can control the angle of the bounce by where it hits on the paddle. I didn't have time to implement that. * Yeah baby! http://www.old-computers.com/museum/computer.asp?st=3&c=1038
|
Luna Wu
Member #16,273
April 2016
|
It was indeed a problem with the logic of the if statements, I fixed it now, I'm still gonna do the angle thing and fix lots of weird things, I was just trying to at least make the ball bounce at first , I gotta be careful with the logic this time thank you so much for the help guys! I'm aware putting everything in main is a bad idea, but that's one of my first allegro5 projects so I found it a little hard to make split functions, I don't know why I found it hard though, , thank you |
|