DZone Snippets is a public source code repository. Easily build up your personal collection of code snippets, categorize them with tags / keywords, and share them with the world
Langton's Ant In Python
The following code simulates <a href="http://en.wikipedia.org/wiki/Langton's_ant">Langton's Ant</a> using Python and PyGame.
A full explanation is given <a href="http://compprog.wordpress.com/2008/02/15/langtons-ant/">here</a>.
#************************************************
# Rules of the game
# 1. If the ant is on a black square, it turns
# right 90 and moves forward one unit
# 2. If the ant is on a white square, it turns
# left 90 and moves forward one unit
# 3. When the ant leaves a square, it inverts
# colour
#
# SEE: http://mathworld.wolfram.com/LangtonsAnt.html
#************************************************
import sys, pygame
from pygame.locals import *
import time
dirs = (
(-1, 0),
(0, 1),
(1, 0),
(0, -1)
)
cellSize = 12 # size in pixels of the board (4 pixels are used to draw the grid)
numCells = 64 # length of the side of the board
background = 0, 0, 0 # background colour; black here
foreground = 23, 23, 23 # foreground colour; the grid's colour; dark gray here
textcol = 177, 177, 177 # the colour of the step display in the upper left of the screen
antwalk = 44, 88, 44 # the ant's trail; greenish here
antant = 222, 44, 44 # the ant's colour; red here
fps = 1.0 / 40 # time between steps; 1.0 / 40 means 40 steps per second
def main():
pygame.init()
size = width, height = numCells * cellSize, numCells * cellSize
pygame.display.set_caption("Langton's Ant")
screen = pygame.display.set_mode(size) # Screen is now an object representing the window in which we paint
screen.fill(background)
pygame.display.flip() # IMPORTANT: No changes are displayed until this function gets called
for i in xrange(1, numCells):
pygame.draw.line(screen, foreground, (i * cellSize, 1), (i * cellSize, numCells * cellSize), 2)
pygame.draw.line(screen, foreground, (1, i * cellSize), (numCells * cellSize, i * cellSize), 2)
pygame.display.flip() # IMPORTANT: No changes are displayed until this function gets called
font = pygame.font.Font(None, 36)
antx, anty = numCells / 2, numCells / 2
antdir = 0
board = [[False] * numCells for e in xrange(numCells)]
step = 1
pause = False
while True:
for event in pygame.event.get():
if event.type == QUIT:
return
elif event.type == KEYUP:
if event.key == 32: # If space pressed, pause or unpause
pause = not pause
elif event.key == 115:
pygame.image.save(screen, "Step%d.tga" % (step))
if pause:
time.sleep(fps)
continue
text = font.render("%d " % (step), True, textcol, background)
screen.blit(text, (10, 10))
if board[antx][anty]:
board[antx][anty] = False # See rule 3
screen.fill(background, pygame.Rect(antx * cellSize + 1, anty * cellSize + 1, cellSize - 2, cellSize - 2))
antdir = (antdir + 1) % 4 # See rule 1
else:
board[antx][anty] = True # See rule 3
screen.fill(antwalk, pygame.Rect(antx * cellSize + 1, anty * cellSize + 1, cellSize - 2, cellSize - 2))
antdir = (antdir + 3) % 4 # See rule 2
antx = (antx + dirs[antdir][0]) % numCells
anty = (anty + dirs[antdir][1]) % numCells
# The current square (i.e. the ant) is painted a different colour
screen.fill(antant, pygame.Rect(antx * cellSize + 1, anty * cellSize + 1, cellSize -2, cellSize -2))
pygame.display.flip() # IMPORTANT: No changes are displayed until this function gets called
step += 1
time.sleep(fps)
if __name__ == "__main__":
main()





