Advertisement
tokyoedtech

Python Asteroids Demo

Feb 5th, 2017
1,845
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 11.15 KB | None | 0 0
  1. #Asteroids by @TokyoEdTech / Written in Python 3.5
  2. #Website: www.christianthompson.com
  3. #YouTube Channel: https://www.youtube.com/channel/UC2vm-0XX5RkWCXWwtBZGOXg
  4. #Working Demo
  5. #Controls:
  6. #Left Arrow - Rotate Left / Right Arrow - Rotate Right
  7. #Up Arrow - Accelerate / Down Arrow - Hyperspace Jump
  8. #Space Bar - Fire Missile
  9.  
  10. import os
  11. import random
  12. import time
  13. import math
  14.  
  15. #Import the Turtle module
  16. import turtle
  17. #Set the screensize
  18. turtle.setup(width=800, height=800)
  19. #Set the animations speed to the maximum
  20. turtle.speed(0)
  21. #Change the background color
  22. turtle.bgcolor("black")
  23. #Change the window title
  24. turtle.title("Asteroids")
  25. #Hide the default turtle
  26. turtle.ht()
  27. #This saves memory
  28. turtle.setundobuffer(1)
  29. #This speeds up drawing
  30. turtle.tracer(0)
  31.  
  32. class Shield(turtle.Turtle):
  33.     def __init__(self):
  34.         turtle.Turtle.__init__(self)
  35.         self.speed(0)
  36.         self.penup()
  37.         self.ht()
  38.         self.frame = 1
  39.         self.strength = 100
  40.    
  41.     def draw(self):
  42.         self.goto(player.xcor() + 20, player.ycor())
  43.         self.setheading(90)
  44.         self.pendown()
  45.         if self.strength > 66:
  46.             self.color("green")
  47.             self.pensize(3)
  48.         elif self.strength > 33 and self.strength <= 66:
  49.             self.color("yellow")
  50.             self.pensize(2)
  51.         elif self.strength > 0 and self.strength <= 33:
  52.             self.color("red")
  53.             self.pensize(1)
  54.         else:
  55.             self.color("black")
  56.             self.strength = 0
  57.  
  58.         if self.strength > 0:
  59.             self.circle(20)
  60.             self.penup()
  61.             self.frame += 1
  62.         else:
  63.             self.clear()
  64.        
  65.         if self.frame == 3:
  66.             self.clear()
  67.             self.frame = 1
  68.  
  69. class Sprite(turtle.Turtle):
  70.     def __init__(self, spriteshape, color, startx, starty):
  71.         turtle.Turtle.__init__(self, shape = spriteshape)
  72.         self.speed(0)
  73.         self.penup()
  74.         self.color(color)
  75.         self.fd(0)
  76.         self.goto(startx, starty)
  77.         self.speed = 1
  78.        
  79.     def move(self):
  80.         self.fd(self.speed)
  81.        
  82.         #Boundary detection
  83.         if self.xcor() > 290:
  84.             self.setx(self.xcor() - 580)
  85.        
  86.         if self.xcor() < -290:
  87.             self.setx(self.xcor() + 580)
  88.        
  89.         if self.ycor() > 290:
  90.             self.sety(self.ycor() - 580)
  91.        
  92.         if self.ycor() < -290:
  93.             self.sety(self.ycor() + 580)
  94.            
  95.     def is_collision(self, other):
  96.         #Distance changes based on shield strength
  97.         if shield.strength > 0:
  98.             if other.size == 3.0:
  99.                 distance = 45
  100.             elif other.size == 2.0:
  101.                 distance = 35
  102.             elif other.size == 1.0:
  103.                 distance = 25
  104.         else:
  105.             if other.size == 3.0:
  106.                 distance = 30
  107.             elif other.size == 2.0:
  108.                 distance = 25
  109.             elif other.size == 1.0:
  110.                 distance = 20
  111.            
  112.         if (self.xcor() >= (other.xcor() - distance)) and \
  113.         (self.xcor() <= (other.xcor() + distance)) and \
  114.         (self.ycor() >= (other.ycor() - distance)) and \
  115.         (self.ycor() <= (other.ycor() + distance)):
  116.             return True
  117.         else:
  118.             return False
  119.                
  120. class Player(Sprite):
  121.     def __init__(self, spriteshape, color, startx, starty):
  122.         Sprite.__init__(self, spriteshape, color, startx, starty)
  123.         self.shapesize(stretch_wid=0.6, stretch_len=1.1, outline=None)
  124.         self.speed = 0
  125.         self.lives = 3
  126.         self.shapesize(stretch_wid=0.6, stretch_len=1.1, outline=None)
  127.         self.thrust = 1
  128.         self.dx = 0
  129.         self.dy = 0
  130.         self.rotation_speed = 0
  131.        
  132.     def turn_left(self):
  133.         self.rotation_speed = 30
  134.         h = self.heading() + self.rotation_speed
  135.         player.setheading(h)
  136.        
  137.     def turn_right(self):
  138.         self.rotation_speed = -30
  139.         h = self.heading() + self.rotation_speed
  140.         player.setheading(h)
  141.                        
  142.     def accelerate(self):
  143.         h = player.heading()
  144.         self.dx += math.cos(h*math.pi/180)*self.thrust
  145.         self.dy += math.sin(h*math.pi/180)*self.thrust
  146.        
  147.     def hyperspace(self):
  148.         #os.system("afplay hyperspace.mp3&")
  149.         x = random.randint(-250, 250)
  150.         y = random.randint(-250, 250)
  151.         self.goto(x, y)
  152.         self.dx *= 0.5
  153.         self.dy *= 0.5
  154.        
  155.     def move(self):    
  156.         player.goto(player.xcor()+self.dx, player.ycor()+self.dy)      
  157.        
  158.         #Boundary detection
  159.         if self.xcor() > 290:
  160.             self.setx(self.xcor() - 580)
  161.        
  162.         if self.xcor() < -290:
  163.             self.setx(self.xcor() + 580)
  164.        
  165.         if self.ycor() > 290:
  166.             self.sety(self.ycor() - 580)
  167.        
  168.         if self.ycor() < -290:
  169.             self.sety(self.ycor() + 580)
  170.  
  171.     def collides(self, asteroid):                      
  172.         if shield.strength > 0:
  173.             x = (asteroid.xcor() + player.xcor()) / 2.0
  174.             y = (asteroid.ycor() + player.ycor()) / 2.0
  175.             explosion.explode(x, y)
  176.             asteroid.destroy()
  177.             game.score += 100
  178.             shield.strength -= int(10 * asteroid.size)
  179.         else:          
  180.             x = (asteroid.xcor() + player.xcor()) / 2.0
  181.             y = (asteroid.ycor() + player.ycor()) / 2.0
  182.             explosion.explode(x, y)
  183.             game.score -= 100
  184.             game.lives -= 1
  185.            
  186.             #Check if player is out of lives. If so, reset.
  187.             if game.lives < 1:
  188.  
  189.                 #Reset game
  190.                 for asteroid in game.asteroids:
  191.                     asteroid.size = 1
  192.                     asteroid.goto(-1000, -1000)
  193.  
  194.                 for asteroid in game.asteroids:                
  195.                     asteroid.destroy()
  196.  
  197.                 #Clear the asteroid list                   
  198.                 try:
  199.                     #Python 3.3 and above              
  200.                     game.asteroids.clear()
  201.                 except:
  202.                     #Python 3.2 and below
  203.                     game.asteroids = []
  204.  
  205.                 game.level = 1
  206.                 game.lives = 3
  207.                 game.score = 0
  208.                 shield.strength = 100
  209.                 player.goto(0, 0)
  210.                 game.start_level()
  211.  
  212.             asteroid.destroy()
  213.        
  214.         game.show_status()
  215.    
  216. class Asteroid(Sprite):
  217.     def __init__(self, spriteshape, color, size, speed, startx, starty):
  218.         Sprite.__init__(self, spriteshape, color, startx, starty)
  219.         self.shapesize(stretch_wid=size, stretch_len=size, outline=None)
  220.         self.speed = speed
  221.         self.size = size
  222.         self.setheading(random.randint(0,360))
  223.  
  224.     def move(self):
  225.         self.fd(self.speed)
  226.  
  227.         if self.size == 3.0:
  228.             left = -272
  229.             right = 272
  230.             top = 272
  231.             bottom = -272
  232.  
  233.         elif self.size == 2.0:
  234.             left = -280
  235.             right = 280
  236.             top = 289
  237.             bottom = -280
  238.  
  239.         elif self.size == 1.0:
  240.             left = -290
  241.             right = 290
  242.             top = 290
  243.             bottom = -290
  244.  
  245.         #Boundary detection
  246.         if self.xcor() > right:
  247.             self.setx(self.xcor() - right * 2)
  248.        
  249.         if self.xcor() < left:
  250.             self.setx(self.xcor() + right * 2)
  251.        
  252.         if self.ycor() > top:
  253.             self.sety(self.ycor() - top * 2)
  254.        
  255.         if self.ycor() < bottom:
  256.             self.sety(self.ycor() + top * 2)
  257.  
  258.     def destroy(self):
  259.             if self.size == 3.0:
  260.                 self.size = 2.0
  261.                 self.speed = 5
  262.  
  263.                 #Append a new asteroid
  264.                 game.asteroids.append(Asteroid("circle", "brown",2.0 ,4 , self.xcor(), self.ycor()))
  265.  
  266.                 #Change Asteroid Size          
  267.                 self.shapesize(stretch_wid=asteroid.size, stretch_len=asteroid.size, outline=None)
  268.  
  269.                 #Change Heading
  270.                 self.setheading(random.randint(0, 360))
  271.  
  272.             elif self.size == 2.0:
  273.                 self.size = 1.0
  274.                 self.speed = 7
  275.  
  276.                 #Append a new asteroid
  277.                 game.asteroids.append(Asteroid("circle", "brown",1.0 ,5 , self.xcor(), self.ycor()))
  278.  
  279.                 #Change Asteroid Size          
  280.                 self.shapesize(stretch_wid=asteroid.size, stretch_len=asteroid.size, outline=None)
  281.  
  282.                 #Change Heading
  283.                 self.setheading(random.randint(0, 360))
  284.  
  285.             elif self.size == 1.0:
  286.                 self.goto(1000, 1000)
  287.                 self.ht()
  288.                 if asteroid in game.asteroids:
  289.                     game.asteroids.remove(asteroid)
  290.  
  291. class Missile(Sprite):
  292.     def __init__(self, spriteshape, color, startx, starty):
  293.         Sprite.__init__(self, spriteshape, color, startx, starty)
  294.         self.shapesize(stretch_wid=0.2, stretch_len=0.4, outline=None)
  295.         self.speed = 20
  296.         self.status = "ready"
  297.         self.goto(-1000, 1000)
  298.        
  299.     def fire(self):
  300.         if self.status == "ready":
  301.             self.goto(player.xcor(), player.ycor())
  302.             self.setheading(player.heading())
  303.             self.status = "firing"
  304.            
  305.     def move(self):
  306.         if self.status == "ready":
  307.             self.goto(-1000, 1000)
  308.        
  309.         elif self.status == "firing":
  310.             self.fd(self.speed)
  311.            
  312.         #Border check
  313.         if self.xcor() < -290 or self.xcor() > 290 or \
  314.             self.ycor()< -290 or self.ycor()> 290:
  315.             self.goto(-1000,1000)
  316.             self.status = "ready"
  317.  
  318. class Particle(Sprite):
  319.     def __init__(self, spriteshape, color, startx, starty):
  320.         Sprite.__init__(self, spriteshape, color, startx, starty)
  321.         self.shapesize(stretch_wid=0.1, stretch_len=0.1, outline=None)
  322.         self.goto(-1000,-1000)
  323.         self.frame = 0.0
  324.        
  325.     def explode(self, startx, starty):
  326.         self.goto(startx,starty)
  327.         self.setheading(random.randint(0,360))
  328.         self.frame = 1.0
  329.         self.myspeed = random.randint(2, 10)
  330.  
  331.     def move(self):
  332.         if self.frame > 0:
  333.             self.fd(self.myspeed)
  334.             self.frame += 1.0
  335.             self.shapesize(stretch_wid=0.3/self.frame, stretch_len=0.3/self.frame, outline=None)
  336.  
  337.         if self.frame > 15.0:
  338.             self.frame = 0.0
  339.             self.goto(-1000, -1000)
  340.  
  341. class Explosion(object):
  342.     def __init__(self):
  343.         self.particles = []
  344.         for i in range(25):
  345.             self.particles.append(Particle("circle", random.choice(["yellow", "red", "orange"]), 0, 0))
  346.    
  347.     def explode(self, x, y):
  348.         for particle in self.particles:
  349.             particle.explode(x, y)
  350.            
  351.     def animate(self):
  352.         for particle in self.particles:
  353.             if particle.frame > 0:
  354.                 particle.move()
  355.  
  356. class Game(object):
  357.     def __init__(self):
  358.         self.level = 1
  359.         self.score = 0
  360.         self.state = "playing"
  361.         self.pen = turtle.Turtle()
  362.         self.lives = 3
  363.         self.asteroids = []
  364.        
  365.     def start_level(self):
  366.         for i in range(self.level):
  367.             self.asteroids.append(Asteroid("circle", "brown", 3.0, 2, random.randint(-300, 300), random.randint(-300, 300)))
  368.  
  369.     def draw_border(self):
  370.         #Draw border
  371.         self.pen.speed(0)
  372.         self.pen.color("white")
  373.         self.pen.pensize(3)
  374.         self.pen.penup()
  375.         self.pen.goto(-300, 300)
  376.         self.pen.pendown()
  377.         for side in range(4):
  378.             self.pen.fd(600)
  379.             self.pen.rt(90)
  380.         self.pen.penup()
  381.         self.pen.ht()
  382.         self.pen.pendown()
  383.        
  384.     def show_status(self):
  385.         self.pen.undo()
  386.         msg = "ASTEROIDS! Level: {}  Score: {}  Lives: {}  Shields: {}".format(self.level, self.score, game.lives, shield.strength)
  387.         self.pen.penup()
  388.         self.pen.goto(-300, 310)
  389.         self.pen.write(msg, font=("Arial", 16, "normal"))
  390.  
  391. #Create my sprites (class instances)
  392. player = Player("triangle", "white", 0, 0)
  393. missile = Missile("triangle", "yellow", 0, 0)
  394. shield = Shield()
  395.  
  396. #Create explosion object
  397. explosion = Explosion()
  398.  
  399. #Create game object
  400. game = Game()
  401.  
  402. #Draw the game border
  403. game.draw_border()
  404.  
  405. #Show the game status
  406. game.show_status()
  407.  
  408. #Start the level
  409. game.start_level()
  410.  
  411. #Keyboard bindings
  412. turtle.onkey(player.turn_left, "Left")
  413. turtle.onkey(player.turn_right, "Right")
  414. turtle.onkey(player.accelerate, "Up")
  415. turtle.onkey(player.hyperspace, "Down")
  416. turtle.onkey(missile.fire, "space")
  417. turtle.listen()
  418.  
  419. #Main game loop
  420. while True:
  421.     turtle.update()
  422.     #time.sleep(0.02)
  423.  
  424.     player.move()
  425.     missile.move()
  426.    
  427.     for asteroid in game.asteroids:
  428.         asteroid.move()
  429.        
  430.         #Check for a collision with the player
  431.         if player.is_collision(asteroid):
  432.             #Do the explosion
  433.             player.collides(asteroid)
  434.            
  435.         #Check for a collision between the missile and the asteroid
  436.         if missile.is_collision(asteroid):
  437.             #Reset the Missile Status  
  438.             missile.status = "ready"
  439.  
  440.             #Increase the score
  441.             game.score += 100
  442.             game.show_status()
  443.            
  444.             #Do the explosion
  445.             x = (asteroid.xcor() + missile.xcor()) / 2.0
  446.             y = (asteroid.ycor() + missile.ycor()) / 2.0
  447.             explosion.explode(x, y)
  448.  
  449.             #If the asteroid is Large, make it small times 2
  450.             asteroid.destroy()
  451.  
  452.     explosion.animate()
  453.    
  454.     #Shield
  455.     shield.draw()
  456.  
  457.     #Check for end of level
  458.     if len(game.asteroids) == 0:
  459.         game.level += 1
  460.         game.start_level()
  461.  
  462.     game.show_status()
  463.  
  464. delay = input("Press enter to finish. > ")
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement