CSCI 150 - Foundations of Computer Science

Fall 2013

Programming Exercises: Chapter 9, part 4


Here is our example from class:
from tkinter import *
import math

class Circle:
    def __init__(self, canvas, x, y, radius, dx, dy):
        self.id = canvas.create_oval(x - radius, y - radius, x + radius, y + radius)
        self.canvas = canvas
        self.dx = dx
        self.dy = dy
        self.radius = radius

    def teleport(self, x, y):
        self.canvas.coords(self.id, x - self.radius, y - self.radius,
                           x + self.radius, y + self.radius)

    def move(self):
        self.canvas.move(self.id, self.dx, self.dy)
        
    def x(self):
        return list(self.canvas.coords(self.id))[0] + self.radius

    def y(self):
        return list(self.canvas.coords(self.id))[1] + self.radius

    def distanceTo(self, other):
        pass # Your code here

    def collidingWith(self, other):
        pass # Your code here


class WrapCircle(Circle):
    def move(self):
        super().move()
        width = self.canvas.winfo_reqwidth()
        height = self.canvas.winfo_reqheight()

        # If it goes out of bounds, make it wrap around

class Ship:
    def __init__(self, canvas, length, turnSpeed):
        self.canvas = canvas
        self.length = length
        self.angle = 0
        self.turnSpeed = turnSpeed
        self.id = None
        self.update()

    def left(self):
        self.angle -= self.turnSpeed
        self.update()

    def right(self):
        self.angle += self.turnSpeed
        self.update()

    def update(self):
        if self.id:
            self.canvas.delete(self.id)
        self.id = self.canvas.create_line(self.x(), self.y(), self.xTip(), self.yTip())        

    def x(self):
        return self.canvas.winfo_reqwidth() / 2

    def y(self):
        return self.canvas.winfo_reqheight() / 2

    def xTip(self):
        return self.x() + self.length * math.cos(self.angle)

    def yTip(self):
        return self.y() + self.length * math.sin(self.angle)

class AsteroidBelt(Frame):
    def __init__(self, master):
        Frame.__init__(self, master)

        self.canvas = Canvas(self, width=300, height=300)
        self.canvas.grid(row=0, column=0)
        self.canvas.bind('<KeyPress>', self.keys)
        self.canvas.focus_set()

        self.ship = Ship(self.canvas, 30, math.pi/12)

        # Modify this to create lots of asteroids moving in random directions
        self.circles = [WrapCircle(self.canvas, 0, 0, 15, 1, 2)]

        # You will need to add another list attribute to represent the missiles
        
        self.move()

    def move(self):
        for circle in self.circles:
            circle.move()
        # Be sure to update missile locations as well

        # After all locations are updated, check for collisions,
        # and remove debris
        
        self.after(100, self.move)

    def keys(self, event):
        if event.keysym == 'Left':
            self.ship.left()
        elif event.keysym == 'Right':
            self.ship.right()
        # Check to see if the space bar is pressed
        # If so, fire a missile

def runGame():
    root = Tk()
    ab = AsteroidBelt(root)
    ab.pack()
    root.mainloop()
Modify this program so that: