Creating a Game in Python Using PyGame – Part One


In order to follow along with this tutorial you will need Python 2.4 and PyGame 1.7.0+ installed. Since I’m doing this all on a Mac and Python 2.4.2 is not available from MacPython or any other site as a disk image I decided to install from source.

If you are try to build Python on a Mac as well you should probably install into the /Library/Frameworks path as explained by this site.

Basically once you have downloaded the source from unpack the tar ball as follows:

tar -zxvf Python-2.4.2.tgz

Once that has finished change to the Python-2.4.2 directory that was just created and install it by issuing the following commands:

./configure --enable-framework
sudo make frameworkinstall

For Windows or Linux you should be able to install easily given the instructions on the Python site.

This will install Python in the /Library/Frameworks path, and create a symlink to the python executable in /use/local/bin, which is not part of the PATH environment variable on new OS X builds, so you will probably want to add it:

export PATH=/usr/local/bin:$PATH

Part One

The full source of this tutorial can be downloaded here.

Python SnakeSo let’s actually start creating this game using PyGame. For our snake image in the game I’m going to use the snake to the left for now. As you can see I’m not artist, but I was able to install the gimp on my Mac and get that image to a point that I think is relatively acceptable. If anyone out there has any graphics skills and can whip me up a better looking python in a 64×64 png I’d gladly use it!

So the first thing we are going to do is create a new PyDev project in Eclipse. I’m going to use Python 2.4 for this project because it is the version that is compatible with my PyGame Installation.

Python foldersThen I’m going to create a new file called, this will be the main file of our game for now. The architecture may change as I go through this and discover better ways to use the files in my projects but for now this will work as a main file. In the directory that I create my project I will also create a subfolder entitled “data” and in that subfolder I will have another folder entitled “images” where I will store the above snake.png image.

Note: A lot of the information in this post was taken from the Pete Shinner’s great Line by Line Chimp and Python Pygame Introduction tutorials.

Now the first thing that we are going to have to do is import the libraries that we are going to need, we’ll also warn the user if the font or sound mixers are not available:

[code lang=”python”]
import os, sys
import pygame
from pygame.locals import *

if not pygame.font: print ‘Warning, fonts disabled’
if not pygame.mixer: print ‘Warning, sound disabled’

Then we’re going to create a class called PyManMain, this is going to be the main class of our game, it will handle all of the main functions in our game, things like the game loop, the screen creation, and keeping track of all of our sprites:

[code lang=”python”]
class PyManMain:
“””The Main PyMan Class – This class handles the main
initialization and creating of the Game.”””

def __init__(self, width=640,height=480):
“””Initialize PyGame”””
“””Set the window Size”””
self.width = width
self.height = height
“””Create the Screen”””
self.screen = pygame.display.set_mode((self.width
, self.height))

As you can see our __init__ function takes two optional parameters height and width, this will be the height and the width of the screen that we create. The __init__ function basically initializes pygame (pygame.init()) and then creates our main screen using the pygame.display.set_mode function.

So far so good! The next thing that we are going to need is a game loop, this is the loop that will process all of the events that PyGame sends our way. To do that, we’re going to add a function to our PyManMain class called MainLoop:

[code lang=”python”]
def MainLoop(self):
“””This is the Main Loop of the Game”””
while 1:
for event in pygame.event.get():
if event.type == pygame.QUIT:

We’ll also add the code to our class that will start out game:

[code lang=”python”]
if __name__ == “__main__”:
MainWindow = PyManMain()

PyGame WindowIf you run this now you will be with a very uninspiring black screen. It may not be much but for the amount of code that we’ve written it’s pretty good.

The next thing that we need to create is out snake sprite. We are going to wrap our snake sprite in it’s own class called snake (of course) and it will be based off of the pygame.sprite.Sprite class. If you want to read more about PyGames sprite and group classes you should read piman’s great sprite tutorial:

[code lang=”python”]
class Snake(pygame.sprite.Sprite):
“””This is our snake that will move around the screen”””

def __init__(self):
self.image, self.rect = load_image(‘snake.png’,-1)
self.pellets = 0

As you can see the Snake class really isn’t doing much besides initializing the Sprite base class and loading the snake image. It also sets pellets to zero, this variable isn’t used yet but it is the number of pellets that our snake has eaten.

You’ll notice that we use load_image to load our snake image. This function is taken from the Line by Line Chimp tutorial. I created a new file for my project called which will contain all helper functions. I put load_image in this file and added the following to the top of

[code lang=”python”]
from helpers import *

Now we have to create an instance of our snake sprite and display it. To do this I created another function in the PyManMain class called LoadSprites, this function will take care of loading all of our sprites:

[code lang=”python”]
def LoadSprites(self):
“””Load the sprites that we need”””
self.snake = Snake()
self.snake_sprites = pygame.sprite.RenderPlain((self.snake))

This function creates the sprite (self.snake = Snake) and then creates a group that contains our snake sprite (self.snake_sprites = pygame.sprite.RenderPlain((self.snake))).

We are also going to have to make some changes to the MainLoop function, we are going to have to load all of our sprites before we enter the while loop:

[code lang=”python”]
“””Load All of our Sprites”””

Then after our event for loop but within the while loop we need to tell PyGame to draw our sprit:

[code lang=”python”]

Python SnakeNow we’re getting somewhere! We’ve got our little PyMan snake displaying himself in the top left corner of our screen. Not too bad.

The next thing that we’re going to want to do is create and display all of our pellets, this isn’t very difficult if you understood the snake sprite above you’ll understand this:

[code lang=”python”]
class Pellet(pygame.sprite.Sprite):

def __init__(self, rect=None):
self.image, self.rect = load_image(‘pellet.png’,-1)
if rect != None:
self.rect = rect

Python pelletThe only difference you’ll see in the pellet class is the fact that we have an optional rect parameter, which lets us place the pellet where ever we want. The pellets I’ve created aren’t the best pellets that I’ve ever seen but just like the snake.png they’ll do for this example.

We then need to load the pellet sprites in our LoadSprites function:

[code lang=”python”]
“””figure out how many pellets we can display”””
nNumHorizontal = int(self.width/64)
nNumVertical = int(self.height/64)
“””Create the Pellet group”””
self.pellet_sprites = pygame.sprite.Group()
“””Create all of the pellets and add them to the
pellet_sprites group”””
for x in range(nNumHorizontal):
for y in range(nNumVertical):
self.pellet_sprites.add(Pellet(pygame.Rect(x*64, y*64, 64, 64)))

Then we have to draw the pellets in out MainLoop:

[code lang=”python”]

Now it’s time to make that snake move, to do so we’re going to have to look at the event loop in our MainLoop. ( for event in pygame.event.get():) What we are going to do is move the snake around when the arrow keys are pressed. To do that we are going to check to see if the event is a KEYDOWN event, and if it is a key down event whether the key being pressed is one of the arrow keys:

[code lang=”python”]
if event.type == pygame.QUIT:
elif event.type == KEYDOWN:
if ((event.key == K_RIGHT)
or (event.key == K_LEFT)
or (event.key == K_UP)
or (event.key == K_DOWN)):

Then we have to add a move function to our snake class that will actually move our snake:

[code lang=”python”]
def move(self, key):
“””Move your self in one of the 4 directions according to key”””
“””Key is the pyGame define for either up,down,left, or right key
we will adjust ourselves in that direction”””
xMove = 0;
yMove = 0;

if (key == K_RIGHT):
xMove = self.x_dist
elif (key == K_LEFT):
xMove = -self.x_dist
elif (key == K_UP):
yMove = -self.y_dist
elif (key == K_DOWN):
yMove = self.y_dist

You’ll notice that the move function references self.x_dist and self.y_dist, these are basically two integers that I set in the snake’s __init__ function, they are the number of pixels that we want the snake to move in the x or y direction. I set mine to 5.

To move the snake we adjust it’s rect so that the next time it is displayed it will be drawn in a different direction. To do that we call the rect.move_ip function with the amount of pixels in the x and y directions to move.

Now we are going to have to add some collision detection to make our snake eat our pellets. Thankfully the spirt and group classes have built in collision detection that we are able to use:

[code lang=”python”]
“””Check for collision”””
lstCols = pygame.sprite.spritecollide(self.snake
, self.pellet_sprites
, True)
“””Update the amount of pellets eaten”””
self.snake.pellets = self.snake.pellets + len(lstCols)

We use the pygame.sprite.spritecollide function to see if our snake sprite collided with any of the pellet sprites. If they did we kill which ever pellet that was hit by passing True as the third parameter. pygame.sprite.spritecollide basically goes through all of the sprites in the group passes and sees if the sprites rect intersects with the sprit passed in as parameter one.

pygame.sprite.spritecollide also returns a list of all the sprites that were collided by our snake, so we use that to update the number of pellets that we have eaten.

The last thing that we our going to do in this tutorial is display the number of pellets that we have eaten to the user:

[code lang=”python”]
if pygame.font:
font = pygame.font.Font(None, 36)
text = font.render(“Pellets %s” % self.snake.pellets
, 1, (255, 0, 0))
textpos = text.get_rect(centerx=self.width/2)
self.screen.blit(text, textpos)

This code is taken from the line by line chimp example with very few changes. Instead of telling the user to hit the chimp for cash, we’re telling them how many pellets that the snake has eaten so far. We need to put the code right right before we draw our sprites in the game loop.

Python SnakeThat’s about it for this example, there is a bit of code in the finished “product” that I didn’t discuss but if you download the full source it the new code should be pretty self explanatory. Now this isn’t a full example by any means and probably isn’t something that you’d really want to base any game off of, but it does give you a pretty basic idea about what is required to create a game in using Python and PyGame.

If you are really interested in creating a game I’d suggest you download the full source and play around with it a bit. I’m also suggest (insist?) that you read the documentation and tutorials provided for you on the main PyGame site, if it wasn’t for them I would have been unable to write this simple tutorial.

Whew, that was a lot a typing, it’s time for me to go make some dinner and have a glass of wine.

Useful links:

  • If you like this post remember to digg it.

    Note: Whew! Many thanks to James for finding the google cahce for me! I looked for it when I first deleted it but couldn’t fine it. Much appreciated!

    Here are some alternate images that were sent to me by a kind reader named Jordan:

    Python Snake
    Python Snake

    99 thoughts on “Creating a Game in Python Using PyGame – Part One”

    1. I just want to say thank you! A great tutorial….nice work. Finally a tutorial which explains things to me in human language so that even I can understand it 😉 Keep up the good work!!

    2. when i try to load the system i get a black screen and an error called: cannot open /data/images/snake.png!

    3. thanks for the tut. i m a newbee to python, today is my first day with python environment. i just run ur tut and is working fine (windows XP with Python 2.5). just it gets crashed when i close(don’t understand, will know soon). anyway thank u for the tut.

    4. Hey man, first i wanna congratulate you for the tutorial. I have managed to learn a lot but i still have a few doubts and im wondering if you could help me with then.

      The major one is that, with that kind of movement sometimes the snake aint into the propper position to go into the pellets way you know, so i have to go back and forth to adjust it into the right position to so i can turn to the desire position. Im not sure if im explaining it propperly. So, is it possible for me to make the snake move exactly one block for each movement? Instead of a free movement to any desire position? That would solve the problem im having.

      Thanks for the tutorial and i would appreciate if you could help me out.

    5. Hey Selsine,
      Really very informatic.. nyc job from ur side :)
      But i need some help as we r building a path nevigation system to find the sortest path on a loaded map using pygame , run a car on that path and making map path blocking sensitivity enable and we all(in group) are newbie with pygame and python as well… So how we can proceed v hav python2.6.2 installed on windows7 OS.

      Waiting for ur kind responce!!

    6. hey, i have the program written exactly like it should, but when i run it nothing happens. it doesnt say there is an error, but the screen doesn not open at all. i am using python 3.1 so i dont know if the codes are the same? i know this tut is if from a while ago, but i wantes to try it haha :)

    7. Pingback: Purses For Cheap
    8. I keep getting ‘main()’ not defined-

      import pygame,time,sys,random,os
      from pygame.locals import*

      print “end import”


      class main:
      print “main”
      “””main game class”””
      def __init__(self,width=640,height=480):
      print “def _init_”
      “””initialise pygame”””
      “””set the window size”””
      “””create the screen”””

      def mainLoop(self):
      “””game loop(main)”””
      while True:
      for event in pygame.event.get():
      if event.type==pygame.QUIT:


      if __name__==”__main__”:
      print “entering main function”
      print “starting main loop”

    9. will,

      Did you put in the tabs after the defs and other loops? From the way my browser sees it, there are no tabs.

    10. I pulled the full source, and the load_image function is not defined anywhere in it. I get this error.

      NameError: global name ‘load_image’ is not defined

    11. Why do you ignore one of the best Python’s parts — it’s PEP-0008 convention on coding style? Functions and class methods should be named in lowercase with words separated by underscore, when CamelCase is used for classes. It confuses a lot when something looks like a class but isn’t a class.

    12. You’ve got a problem with you’re appostrophies on this page. They all look like this “’”.

    13. Fantastic goods from you, man. I have understand your stuff previous to and you are just extremely wonderful.
      I really like what you’ve acquired here, certainly like what you
      are saying and the way in which you say it. You make it enjoyable and you still care for to keep it wise.
      I cant wait to read much more from you. This is actually
      a wonderful web site.

    14. This is the right webpage for everyone who would like
      to understand this topic. You know a whole lot its almkost tough to argue with
      you (not that I personally would want to…HaHa). You certainly put a brand new spin on a
      topic that’s been written about for many years.
      Excellent stuff, just great!

    15. You can definitely see your expertise within the article you write.
      The world hopes for even more passionate writers such as you who are not afraid to say how they believe.
      At all times follow your heart.

    16. you can remove the key delay when moving the snake by checking for keys with pygame.key.get_pressed() rather than events.

      while 1:
      for event in pygame.event.get():
      if event.type == pygame.QUIT:

      pressed = pygame.key.get_pressed()
      if pressed[pygame.K_RIGHT]: self.snake.move(K_RIGHT)
      if pressed[pygame.K_LEFT]: self.snake.move(K_LEFT)
      if pressed[pygame.K_UP]: self.snake.move(K_UP)
      if pressed[pygame.K_DOWN]: self.snake.move(K_DOWN)

    17. You’re so awesome! I don’t suppose I’ve truly read anything like this before.
      So nice to find someone with original thoughts on this topic.
      Seriously.. thank you for starting this up. This web site is one thing that is needed on the
      web, someone with some originality!

    18. First of all I want to say terrific blog! I had a quick question that I’d
      like to ask if you do not mind. I was curious to know how you center yourself and clear
      your head prior to writing. I’ve had a tough time clearing my mind in getting my ideas out.

      I do take pleasure in writing however it just seems like the first 10 to 15
      minutes are usually lost just trying to figure
      out how to begin. Any recommendations or hints? Many thanks!

    19. Hello, i believe that i noticed you visited my website so
      i came to go back the want?.I’m trying to find issues
      to improve my web site!I guess its adequate
      to make use of some of your ideas!!

    20. Hiya very cool website!! Man .. Beautiful .. Amazing .. I’ll bookmark
      your site and take the feeds additionally? I am
      happy to seek out so many useful information here within the post, we’d like work out extra techniques in this regard, thanks
      for sharing. . . . . .

    21. of course like your web site but you have to take a look
      at the spelling on several of your posts. Many of them are rife with spelling problems and I
      find it very troublesome to tell the truth
      on the other hand I’ll surely come back again.

    22. Thanks for a marvelous posting! I truly enjoyed reading it,
      you can be a great author. I will make certain to bookmark your blog and will often come back from now on. I
      want to encourage continue your great work, have
      a nice holiday weekend!

    23. Oh my goodness! Amazing article dude! Thank you, However I am having issues with your RSS.

      I don’t know the reason why I cannot join it. Is there anybody else
      getting the same RSS issues? Anyone that knows the
      solution can you kindly respond? Thanks!!

    24. I savour, lead to I found exactly what I used to be having a look for.
      You have ended my four day long hunt! God Bless you man. Have a great day.

    25. Excellent site you’ve got here.. It’s hard to find high-quality writing like yours
      nowadays. I seriously appreciate people like you!
      Take care!!

    26. You made some respectable factors there. I regarded on the web for the issue and found most people will go together with with your website.

    27. Hi webmaster, i’ve been reading your articles for some time and I
      really like coming back here. I can see that you probably don’t make money on your site.
      I know one interesting method of earning money, I think you will like
      it. Search google for: dracko’s tricks

    28. I see you don’t monetize your site, don’t waste your traffic, you can earn additional cash every month.
      You can use the best adsense alternative for any type of website (they approve all websites), for
      more details simply search in gooogle: boorfe’s tips monetize
      your website

    29. The next time I read a blog, I hope that it does not fail
      me just as much as this one. I mean, I know it was my choice to read, however I truly thought you’d have something interesting to
      talk about. All I hear is a bunch of whining about something you could possibly fix if you weren’t too busy seeking

    Leave a Reply

    Your email address will not be published. Required fields are marked *

    You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>