05 Conway's Life

The final project for this class will require you to create a python program with a graphical user interface or GUI. The GUI is something you're already used to - windows, a mouse, pull-down menus, buttons, scroll-bars etc. To date your programs have used a command line interface, or CLI, where the user types parameters or commands using just a keyboard when prompted by the computer. Output from a CLI program is typically a simply formatted table of data, or streams of text.
 
This project preparation will teach you how to create windows, draw shapes and colors, and respond to program events, such as keys being pressed.
Part 1: Background Reading
 
There's a bunch of new material to learn when you start making GUI programs. We'll use a game creation libarary called PyGame to create the graphical elements of the program. Go to http://inventwithpython.com/chapters/ and start reading chapter 17. This will show you how to create a window and start drawing objects inside it using PyGame. The full reading assignment is chapters 17-20. 
 
 
 Part 2: Chessboard
 
After you've completed part 1 above, write a program that creates a window with an 8x8 chessboard, with red and black squares. When the user presses the space bar, the chessboard must flip its colors, that is, the squares must alternate between the two colors, while maintaining the chessboard pattern. 
 
 
 
Figure 1: Chessboard
 
Part 3: Conway's Life Algorithm
 
After you complete part 2 above, you must research the Life alogrithm first created by John Conway. You will create a 64x64 cell universe that evolves its cells using the Life algorithm. The heart of your program will be two functions, called count_neighbors(), and evolve(). The Doctests for the functions are shown below.
 
The main() function of your program should:
  1. Create the universe and randomly populate it with cells (e.g. 1 in 5 chance of a cell being occupied),
  2. Open a graphical window that draws the universe of cells and starts evolving it
  3. Pressing the space-bar should evolve the unverse by one step and pause
  4. Pressing 'q' or 'Q' must quit the program gracefully
  5. Pressing any other key should evolve the universe continuously (i.e. no pausing)
 
Figure 2: PyLife
 
 
 def count_neighbors(mat, row, col):
    """
    Checks the 8 neighbors of the cell located at mat[row][col] and
    returns the number of neighbors.
   
    mat = NxN matrix that stores the state of the universe.
    row = row in universe of the cell we're evolving
    col = column in universe of the cell we're evolving
 
    >>> count_neighbors( [[0, 1, 0], [1, 0, 1], [0, 1, 0]] , 2 , 1 )
    2

    >>> count_neighbors( [[1, 0, 0], [0, 1, 1], [1, 0, 0]] , 1 , 1 )
    3

    >>> count_neighbors( [[0, 0, 0], [1, 1, 0], [0, 1, 1]] , 2 , 2 )
    2

    >>> count_neighbors( [[0, 1, 0], [0, 1, 1], [1, 0, 0]] , 0 , 1 )
    2

    >>> count_neighbors( [[1, 1, 1], [0, 1, 0], [0, 0, 1]] , 1 , 1 )
    4

    >>> count_neighbors( [[0, 1, 0], [1, 0, 1], [0, 1, 0]] , 2 , 1 )
    2
    """
 
 
def evolve(mat):
    """
    Steps the entire life universe by 1 generation. The doctest
    verifies the 'blinker' evolution.
 
        . * .      . . .       . * .
        . * . ---> * * * --->  . * .
        . * .      . . .       . * .
   
    >>> evolve( [[0, 1, 0], [0, 1, 0], [0, 1, 0]])
    [[0, 0, 0], [1, 1, 1], [0, 0, 0]]
 
    >>> evolve( [[0, 0, 0], [1, 1, 1], [0, 0, 0]])
    [[0, 1, 0], [0, 1, 0], [0, 1, 0]]
    """