Detecting Collisions


In most games, when two things collide, there's a clear result. It can be as simple as a 2-D character running into a boundary that won't let him pass, or as spectacular as a 3-D scene where an asteroid tears through the hull of a massive mother ship. Either way, there's a need to detect when objects collide.

Introducing the Slippery Pizza Program

The Slippery Pizza program is an extension of the Moving Pan program. In the Slippery Pizza program, the user controls a pan with the mouse, just like in the Moving Pan program. But this time, there's a pizza sprite on the screen. The user can move the pan toward the pizza, but as soon as he or she reaches it, the slippery pizza moves to a new, random screen location. Figures 11.14 and 11.15 show the program in action.

click to expand
Figure 11.14: The player almost reaches the pizza.

click to expand
Figure 11.15: The slippery pizza gets away again.

Setting Up the Program

The initial code is taken from the Moving Pan program, with one minor addition:

 # Slippery Pizza Program # Demonstrates testing for sprite collisions # Michael Dawson 5/12/03 import random from livewires import games SCREEN_WIDTH = 640 SCREEN_HEIGHT = 480 

The one new thing I do is import our old friend the random module. This allows me to generate a new, random location for the pizza sprite after the collision.

Creating the Pan Class

I create a new Pan class by adding some code for the collision detection:

 class Pan(games.Sprite):     """ A pan. Controlled by the mouse. """     def __init__(self, screen, x, y, image):         self.init_sprite(screen = screen, x = x, y = y, image = image)     def moved(self):         """ Move to mouse position. """         x, y = self.screen.mouse_pos()         self.move_to(x,y)         self.check_collide()     def check_collide(self):         """ Check for collision with pizza. """         if self.overlapping_objects():             pizza = self.overlapping_objects()[0]             pizza.handle_collide() 

In the last line of moved(), I invoke the Pan method check_collide(). The check_collide() method invokes the Pan object's overlapping_objects() method, which returns a list of all of the objects that overlap with it. If there are any objects in the list, the first element of the list (which will be the Pizza object, since it's the only other object on the graphics screen) is assigned to pizza. Finally, the Pizza object's handle_collide() method is invoked so the object can react to the collision.

Creating the Pizza Class

Next, I create a new Pizza class:

 class Pizza(games.Sprite):     """ A slippery pizza. """     def __init__(self, screen, x, y, image):         self.init_sprite(screen = screen, x = x, y = y, image = image)     def handle_collide(self):         """ Move to a random screen location. """         x = random.randrange(SCREEN_WIDTH)         y = random.randrange(SCREEN_HEIGHT)         self.move_to(x,y) 

The Pizza class constructor method is the same as in the Pizza Sprite program. However, I add the handle_collide() method, which generates random screen coordinates, (x,y), and moves the Pizza object to this new location. This method is invoked by the Pan object when it collides with the Pizza object.

Writing the Main Program

Here's the main section of the program:

 # main my_screen = games.Screen(SCREEN_WIDTH, SCREEN_HEIGHT) wall_image = games.load_image("wall.jpg", transparent = False) my_screen.set_background(wall_image) x = random.randrange(SCREEN_WIDTH) y = random.randrange(SCREEN_HEIGHT) pizza_image = games.load_image("pizza.bmp") Pizza(screen = my_screen, x = x, y = y, image = pizza_image) pan_image = games.load_image("pan.bmp") Pan(screen = my_screen,      x = SCREEN_WIDTH/2, y = SCREEN_HEIGHT/2,      image = pan_image) my_screen.mouse_visible(False) my_screen.mainloop() 

First, I initialize the Screen object and load a background, like always. Next, I create two objects, a Pizza object and a Pan object. I generate a random set of screen coordinates for the Pizza object and place the Pan object in the middle of the screen. Then, I set the mouse pointer to invisible. Finally, I kick everything off with my_screen.mainloop().




Python Programming for the Absolute Beginner
Python Programming for the Absolute Beginner, 3rd Edition
ISBN: 1435455002
EAN: 2147483647
Year: 2003
Pages: 194

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net