Created
September 24, 2016 18:51
-
-
Save ssophwang/390051821cc04a161c66f34096b9c2c9 to your computer and use it in GitHub Desktop.
Super_Alien.py
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from scene import * | |
import json | |
import sound | |
import random | |
import math | |
A = Action | |
standing_texture = Texture('plf:AlienBlue_front') | |
walk_textures = [Texture('plf:AlienBlue_walk1'), Texture('plf:AlienBlue_walk2')] | |
jump_texture = Texture('plf:AlienBlue_jump') | |
swim_textures = Texture('plf:AlienBlue_swim1'), Texture('plf:AlienBlue_swim2') | |
hit_texture = Texture('plf:AlienBlue_hit') | |
class super_gem(SpriteNode): | |
def __init__(self, **kwargs): | |
SpriteNode.__init__(self, 'plc:Gem_Blue', **kwargs) | |
class good_gem(SpriteNode): | |
def __init__(self, **kwargs): | |
SpriteNode.__init__(self, 'plc:Gem_Green', **kwargs) | |
class Evil(SpriteNode): | |
def __init__(self, img, power, speed, **kwargs): | |
self.power = power | |
self.myspeed = speed | |
SpriteNode.__init__(self, img, **kwargs) | |
class Health_Pack(SpriteNode): | |
def __init__(self, img, heal, **kwargs): | |
self.heal = heal | |
SpriteNode.__init__(self, img, **kwargs) | |
class Awesome_Stuff(SpriteNode): | |
def __init__(self, img, duration, **kwargs): | |
self.duration = duration | |
SpriteNode.__init__(self, img, **kwargs) | |
background_objects_json_str = ''' | |
[{"x": 675, "y": 64, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 610, "y": 64, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 545, "y": 64, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 480, "y": 64, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 825, "y": 180, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 890, "y": 180, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 675, "y": 350, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 740, "y": 350, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 505, "y": 64, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 825, "y": 180, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 890, "y": 180, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 675, "y": 350, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 50, "y": 450, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 115, "y": 450, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 200, "y": 300, "w": 200, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1300, "y": 200, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1365, "y": 200, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1430, "y": 200, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1495, "y": 200, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1165, "y": 400, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1230, "y": 400, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 1295, "y": 400, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 900, "y": 600, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}, | |
{"x": 965, "y": 600, "w": 65, "h": 50, "img": "plf:Ground_PlanetMid"}]''' | |
goodie_objects_json_str = ''' | |
[]''' | |
awesome_objects_json_str = ''' | |
[{"x": 2600, "y": 70, "w": 60, "h": 70, "img": "plf:SwordSilver", "duration": 360}, | |
{"x": 2650, "y": 70, "w": 70, "h": 70, "img": "plf:ShieldSilver", "duration": 360}]''' | |
baddie_objects_json_str = ''' | |
[{"x": 600, "y": 400, "w": 150, "h": 150, "img": "emj:Alien_Monster", "power": 50, "speed":0.5}, | |
{"x": 1400, "y": 61, "w": 70, "h": 70, "img": "plf:Enemy_Barnacle", "power":1, "speed":0}, | |
{"x": 1500, "y": 80, "w": 70, "h": 79, "img": "plf:Enemy_Fly", "power": 20, "speed":0.7}, | |
{"x": 1800, "y": 100, "w": 70, "h": 70, "img": "plf:Enemy_Bee", "power": 20, "speed":0.6}]''' | |
water_objects_json_str = ''' | |
[{"x": -100, "y": -100, "w": 30, "h": 24, "img": "plf:Tile_Water"}, | |
{"x": -100, "y": -100, "w": 30, "h": 24, "img": "plf:Tile_WaterTop_high"}]''' | |
health_pack_objects_json_str = ''' | |
[{"x": 932, "y": 660, "w": 60, "h": 57, "img": "emj:Heart_Growing", "heal": 50}, | |
{"x": 515, "y": 700, "w": 70, "h": 60, "img": "emj:Heart", "heal": 25}]''' | |
def calculate_overlaps(actor_frame,tile_frame): | |
if actor_frame.x + actor_frame.w/2 <= (tile_frame.x + tile_frame.w/2): | |
x_overlap = actor_frame.x + actor_frame.w - tile_frame.x | |
x_postion = 'left' | |
else: | |
x_overlap = tile_frame.x + tile_frame.w - actor_frame.x | |
x_postion = 'right' | |
if (actor_frame.y + actor_frame.h/2) >= (tile_frame.y + tile_frame.h/2): | |
y_overlap = tile_frame.y + tile_frame.h - actor_frame.y | |
y_position = 'above' | |
else: | |
y_overlap = actor_frame.y + actor_frame.h - tile_frame.y | |
y_position = 'below' | |
return(x_overlap, y_overlap, x_postion, y_position) | |
class GameEnvironment(object): | |
def __init__(self): | |
self.background_speed = 1 | |
self.jump = 409 | |
self.gravity = -500 | |
class MyScene (Scene): | |
def setup(self): | |
self.env = GameEnvironment() | |
self.ground = Node(parent=self) | |
groundimage = 'plf:Ground_PlanetMid' | |
w = SpriteNode(groundimage).size.w | |
h = SpriteNode(groundimage).size.h | |
x = 0 | |
while x <= 2 * self.size.w*3: | |
tile = SpriteNode(groundimage, position=(x, h/2)) | |
self.ground.add_child(tile) | |
x += w | |
self.background_color = 'midnightblue' | |
self.background_objects = [] | |
self.good_objects = [] | |
self.bad_objects = [] | |
self.awesome_objects = [] | |
json_object = json.loads(background_objects_json_str) | |
goodie_objects = json.loads(goodie_objects_json_str) | |
awesome_object = json.loads(awesome_objects_json_str) | |
baddie_objects = json.loads(baddie_objects_json_str) | |
for i in range(15): | |
for j in range(11): | |
item = SpriteNode('plf:Tile_Water') | |
item.size = (70,70) | |
item.anchor_point = (0.5, 0) | |
item.position = (i*70 + 1060, j*70 + 64) | |
self.add_child(item) | |
for x in json_object: | |
item = SpriteNode(x['img']) | |
item.anchor_point = (0.5, 0) | |
item.position = (x['x'], x['y']) | |
item.size = (x['w'], x['h']) | |
self.add_child(item) | |
self.background_objects.append(item) | |
for x in awesome_object: | |
item = Awesome_Stuff(x['img'], x['duration']) | |
item.anchor_point = (0.5, 0) | |
item.position = (x['x'], x['y']) | |
item.size = (x['w'], x['h']) | |
self.add_child(item) | |
self.awesome_objects.append(item) | |
for i in range(26): | |
for j in range(8): | |
r = random.uniform(1,2) | |
if r <= 1.25: | |
item = super_gem() | |
item.size = (60,70) | |
elif r <= 1.75: | |
item = good_gem() | |
item.size = (45,55) | |
else: | |
item = SpriteNode('plc:Gem_Orange') | |
item.size = (40,50) | |
item.anchor_point = (0.5, 0) | |
item.position = (i*80 + 25, j*60 + 315) | |
self.add_child(item) | |
self.good_objects.append(item) | |
for x in baddie_objects: | |
item = Evil(x['img'], x['power'], x['speed']) | |
item.anchor_point = (0.5, 0) | |
item.position = (x['x'], x['y']) | |
item.size = (x['w'], x['h']) | |
self.add_child(item) | |
self.bad_objects.append(item) | |
self.health_pack_objects = [] | |
json_object = json.loads(health_pack_objects_json_str) | |
for x in json_object: | |
item = Health_Pack(x['img'], x['heal']) | |
item.anchor_point = (0.5, 0) | |
item.position = (x['x'], x['y']) | |
item.size = (x['w'], x['h']) | |
self.add_child(item) | |
self.health_pack_objects.append(item) | |
self.player = SpriteNode(standing_texture) | |
self.player.anchor_point = (0.5, 0) | |
self.player_actual_h = 78 | |
self.player_actual_w = 60 | |
self.landed_objects = None | |
score_font = ('Futura', 40) | |
self.score_label = LabelNode('0', score_font, parent=self) | |
self.score_label.position = (self.size.w/2, self.size.h - 80) | |
self.score_label.z_position = 1 | |
life_font = ('Futura', 40) | |
self.life_label = LabelNode('Life:' + str('100'), score_font, parent=self) | |
self.life_label.position = (self.size.w/2, self.size.h - 30) | |
self.life_label.z_position = 1 | |
self.add_child(self.player) | |
self.new_game() | |
def new_game(self): | |
self.walk_step = -1 | |
self.player.position = (80, 63) | |
self.player_y_speed = 0.0 | |
self.player_x_speed = 0.0 | |
self.max_speed = 30.0 | |
self.player_landed = True | |
self.player_jumped = False | |
self.score = 0 | |
self.score_label.text = 'Score:' + str('0') | |
self.life = 100 | |
self.life_label.text = 'Life:' + str('100') | |
self.screen_number = 1 | |
self.firece = False | |
self.time = 0 | |
if self.screen_number == 2: | |
self.player.texture = swim_textures[1] | |
else: | |
self.player.texture = standing_texture | |
def player_hit(self): | |
self.player.texture = hit_texture | |
self.player.run_action(A.sequence([A.rotate_to(2*math.pi), A.rotate_to(0)])) | |
def update_player(self): | |
g = gravity() | |
old_x = self.player.position.x | |
old_y = self.player.position.y | |
y = self.player.position.y | |
x = self.player.position.x | |
if self.firece == True: | |
self.time += 1 | |
self.player.color = (.72, .0, .19) | |
if self.time == 700: | |
self.firece = False | |
self.player.color = (1, 1, 1) | |
if y <= 63: | |
self.player_landed = True | |
if self.player_landed == False: | |
self.player.texture = jump_texture | |
if abs(g.y) <= 0.05 and self.player_landed: | |
self.player_x_speed = 0 | |
if abs(g.y) > 0.05 and self.player_landed: | |
self.player_x_speed = -g.y * self.max_speed | |
self.player.x_scale = -cmp(g.y, 0) | |
step = int(self.player.position.x / 40) % 2 | |
if step != self.walk_step and self.screen_number != 2: | |
self.player.texture = walk_textures[step] | |
sound.play_effect('rpg:Footstep00', 0.05, 1.0 + 0.5 * step) | |
elif self.screen_number == 2: | |
self.player.texture = swim_textures[step] | |
self.walk_step = step | |
elif self.player_landed and self.screen_number != 2: | |
self.player.texture = standing_texture | |
self.walk_step = -1 | |
elif self.screen_number == 2: | |
self.player.texture = swim_textures[1] | |
self.walk_step = -1 | |
x = max(0, min(self.size.w, x + self.player_x_speed)) | |
if self.player_jumped: | |
self.player_jumped = False | |
self.player_landed = False | |
self.player_y_speed = self.env.jump | |
elif not self.player_landed: | |
self.player_y_speed = self.player_y_speed + self.env.gravity * self.dt | |
if not self.player_landed: | |
y += self.player_y_speed * self.dt | |
if y <= 63: | |
y = 63 | |
desired_frame = Rect(x-self.player_actual_w/2, y, self.player_actual_w, self.player_actual_h) | |
if self.landed_objects: | |
(x_overlap, y_overlap, x_position, y_position) = calculate_overlaps(desired_frame, self.landed_objects.frame) | |
if x_overlap < 0: | |
self.player_landed = False | |
self.landed_objects = None | |
for object in self.background_objects: | |
(x_overlap, y_overlap, x_position, y_position) = calculate_overlaps(desired_frame, object.frame) | |
if x_overlap < 0 or y_overlap < 0: | |
new_frame = desired_frame | |
else: | |
if x_overlap < y_overlap: | |
if x_position == 'left': | |
self.player_x_speed = 0 | |
new_x = desired_frame.x - x_overlap | |
else: | |
new_x = desired_frame.x + x_overlap | |
desired_frame = Rect(new_x,desired_frame.y,desired_frame.w,desired_frame.h) | |
else: | |
self.player_y_speed = 0 | |
if y_position == 'above': | |
new_y = desired_frame.y + y_overlap | |
self.player_landed = True | |
self.landed_objects = object | |
else: | |
new_y = desired_frame.y - y_overlap | |
desired_frame = Rect(desired_frame.x,new_y,desired_frame.w,desired_frame.h) | |
self.player.position = (desired_frame.x + desired_frame.w/2, desired_frame.y) | |
def collect_item(self, item, value=10): | |
if value == 100: | |
sound.play_effect('arcade:Powerup_1') | |
elif item in self.bad_objects: | |
sound.play_effect('arcade:Explosion_2') | |
elif value == 25: | |
sound.play_effect('arcade:Coin_1') | |
elif value == 0: | |
sound.play_effect('arcade:Laser_4') | |
elif value == 10: | |
sound.play_effect('digital:PowerUp7') | |
if not (isinstance(item, Evil) and item.myspeed == 0) or self.firece == True: | |
item.remove_from_parent() | |
if item in self.good_objects: | |
self.good_objects.remove(item) | |
self.score += value | |
self.score_label.text = 'Score:' + str(self.score) | |
elif item in self.bad_objects: | |
if item.myspeed != 0 or self.firece == True: | |
self.bad_objects.remove(item) | |
if self.firece == False: | |
self.life -= item.power | |
self.life_label.text = 'Life:' + str(self.life) | |
else: | |
self.score += 1000 | |
self.score_label.text = 'Score:' + str(self.score) | |
elif item in self.awesome_objects: | |
self.awesome_objects.remove(item) | |
self.score += value | |
self.score_label.text = 'Score:' + str(self.score) | |
else: | |
self.health_pack_objects.remove(item) | |
self.life += item.heal | |
self.life_label.text = 'Life:' + str(self.life) | |
def check_item_collisions(self): | |
player_hitbox = Rect(self.player.position.x - self.player_actual_w/2, self.player.position.y, self.player_actual_w, self.player_actual_h) | |
for item in list(self.good_objects) + self.bad_objects + self.health_pack_objects + self.awesome_objects: | |
if item.frame.intersects(player_hitbox): | |
if isinstance(item, super_gem): | |
self.collect_item(item, 100) | |
elif isinstance(item, Awesome_Stuff): | |
self.collect_item(item, 0) | |
self.firece = True | |
elif isinstance(item, good_gem): | |
self.collect_item(item, 25) | |
elif isinstance(item, Evil): | |
self.collect_item(item) | |
self.player_hit() | |
elif isinstance(item, Health_Pack): | |
self.collect_item(item) | |
else: | |
self.collect_item(item, 10) | |
def shift_screen(self, direction): | |
if direction == 'right': | |
self.screen_number += 1 | |
else: | |
self.screen_number -= 1 | |
for node in self.children: | |
if not isinstance(node, LabelNode): | |
if direction == 'right': | |
node.position = (node.position.x - self.size.w, node.position.y) | |
else: | |
node.position = (node.position.x + self.size.w, node.position.y) | |
def update_baddies(self): | |
for item in self.bad_objects: | |
(a_x, a_y) = self.player.position | |
(x, y) = item.position | |
l = math.sqrt((x - a_x)**2 + (y - a_y)**2) | |
dx = (x - a_x)/l * item.myspeed | |
dy = (y - a_y)/l * item.myspeed | |
if self.firece == True: | |
item.position = item.position + (dx, dy) | |
else: | |
item.position = item.position - (dx, dy) | |
def player_dead(self): | |
self.game_over = True | |
sound.play_effect('arcade:Explosion_1') | |
self.player.texture = hit_texture | |
self.player.run_action(A.move_by(0, -150)) | |
self.run_action(A.sequence(A.wait(2*self.speed), A.call(self.new_game))) | |
def update(self): | |
self.check_item_collisions() | |
self.update_player() | |
self.update_baddies() | |
if self.player.position.x == self.size.w and self.screen_number <= 2: | |
self.shift_screen('right') | |
elif self.player.position.x == 0 and self.screen_number > 1: | |
self.shift_screen('left') | |
def touch_began(self, touch): | |
if self.player_landed or self.screen_number == 2: | |
self.player_jumped = True | |
self.player_landed = False | |
sound.play_effect('game:Boing_1') | |
run(MyScene(), LANDSCAPE) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment