Simple Video Games are Event-Driven Programs

This lesson is much harder than the other lessons and is probably not something students are going to finish in one or two sessions.

This program and lesson introduce students to Object-Oriented Programming. Students must also learn about lists and boolean values along with if statements.

There isn't much more to learn to complete this program. Of course, it is event-driven so to complete the program the students will have to add new event handlers and modify some of the existing event handlers.

Perhaps the most confusing part of the program are the invisible buttons. There is an invisible button below each pile of cards so that when you click on a pile of cards the program will respond to the button click.

Be sure to have students copy the code provided to the right (they can get the code by clicking on the picture), the cards.zip file, and the card.py file and place all files in the same directory. They must also unzip the cards.zip file. This zip file has all the pictures of the cards for the game.

A solution is not provided here to this lesson. However, I would email the solution to any teacher that would like it so they can study it and help students. I do not want copies made of the solution since this is a project I use in College level courses that I teach.

A Solitaire Card Game

In the last lesson we learned how to write an event-driven program. In this session we do some more event-driven programming to implement a simple solitaire card game.

To learn how to implement a card game we'll dive into the world of Object-Oriented Programming. We've been using objects in several of the lessons so far. In the last few programs we've created a Turtle object and named it t. Turtle is called a class and t is a reference to an object of that class.

We can write our own classes so we can make objects of our own design. For instance, we might want to create a Button class. A Button object can be clicked in our program and can respond to those mouse clicks. The figure below shows the beginning of a Button class.

Because of the size of this program not all the code can be shown here in this web page. If you click on the picture above, you'll see all the code for the program and you can copy it. To get this code to work, you must also have the card images that this code uses. You can get them by clicking this cards.zip link. You must also have the card.py code. You must unzip the cards.zip file and put it in the same directory as the card.py code and the code provided here.

There are several new things to learn about in this lesson. First, you need to learn about classes and how to make an object of a class. You also need to learn about if statements and how they work. This may be too much to learn about in one or two sessions and you may have to do some additional reading to figure it all out.

Now You Try It

This program currently lets you click on a card and move it to a correct pile. However, Aces need to move to the top row. When a card can go to the top row it should be able to move there. When the pile of cards is clicked it should move three and turn over the cards so the top one can be seen and used.

To implement turning the cards over you need to do a few things. For instance, you need to create a pickupPile.

pickupPile = [ ] 

Then, you need to create a button for the deck. This should be done before the deck of cards is created so it ends up underneath the deck.

aButton = ColorButton(t,"Deck",65,690,70,120,\
			cardPileHandler,"black","white")
buttonList.append(aButton)

Finally, to get this to work, you must write the cardPileHandler function above to handle the button click events. The card pile handler moves cards from the deck (called cards in the code) to the pickupPile. When the card list is empty, all the pickupPile cards are moved back to the card list.

def cardPileHandler():
	if len(cards) == 0:
 		while len(pickupPile) > 0:
 			card = pickupPile.pop()
 			card.setFaceDown()
 			cards.append(card)
 			card.goto(100,750)
 		return
 
	if len(cards) > 0:
 		card = cards.pop()
 		card.setFaceUp()
 		pickupPile.append(card)
 		card.goto(200,750)
 
	if len(cards) > 0:
 		card = cards.pop()
 		card.setFaceUp()
 		pickupPile.append(card)
 		card.goto(200,750)
 
	if len(cards) > 0:
 		card = cards.pop()
 		card.setFaceUp()
 		pickupPile.append(card)
 		card.goto(200,750)

There is quite a bit left to do to make this a fun game. It's not trivial, but perhaps you can get it to work if you examine the provided code so you can see how it works. Good luck with this lesson! It's an extra tough one.