A simple game made as a hobby. Use the mouse to control the starship and collect the gems. The faster you collect them the better. Needs pygame (2.1.2) to run.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 

147 lines
3.5 KiB

#!/usr/bin/env python3
from sys import argv
import pygame as pg
# locals
from ship import Ship
from gem import Gem
from block import Block
from starfield import Starfield
from read_level import read_level
# Colors
BLACK = (0,)*3
WHITE = (255,)*3
# Graphical Environment
WIN_SIZE = (640, 480)
MAX_FPS = 60
# Game constants
# Sprite positions
if len(argv) >= 2:
(start, gem_pos, block_pos) = read_level(argv[1])
else:
start = (0,0)
gem_pos = [(100,100)]
block_pos = []
# Setup
pg.init()
clock = pg.time.Clock()
font = pg.font.SysFont('Courier',24)
pg.display.set_caption(f"Space Collector")
screen = pg.display.set_mode(WIN_SIZE)
scr_rect = screen.get_rect()
map_rect = pg.Rect(
(start[0]-scr_rect.width/2,
start[1]-scr_rect.height/2),
scr_rect.size
)
the_starfield = Starfield(screen);
the_ship = Ship(start,scr_rect)
the_ship.rect.x = scr_rect.centerx - the_ship.rect.width / 2
the_ship.rect.y = scr_rect.centery - the_ship.rect.height / 2
disp_sprites = pg.sprite.Group()
gems = pg.sprite.Group(map(Gem,gem_pos))
blocks = pg.sprite.Group(map(Block, block_pos))
moving = pg.sprite.Group(gems,blocks)
# Game loop
carry_on = True
win = False
while carry_on:
# Quitting states
for event in pg.event.get():
if event.type == pg.QUIT:
carry_on = False
elif event.type==pg.KEYDOWN:
if event.key==pg.K_ESCAPE:
carry_on = False
### Game Logic ###
mouse_events = pg.mouse.get_pressed()
if mouse_events[0]:
the_ship.deceleration = 0
the_ship.velocity += 1
if mouse_events[2]:
the_ship.deceleration = 1
mousev = pg.math.Vector2(pg.mouse.get_pos())
mousev -= scr_rect.center
# ship movement
if mousev.length() > the_ship.SIZE/2:
the_ship.direction += mousev.normalize()/(the_ship.velocity+1)
the_ship.direction.normalize_ip()
the_ship.velocity = max(the_ship.velocity - the_ship.deceleration, 0)
if the_ship.velocity == 0:
the_ship.deceleration = 0
# Move ship
the_ship.change = (the_ship.velocity*the_ship.direction)
the_ship.map_pos.x += round(the_ship.change.x)
the_ship.map_pos.y += round(the_ship.change.y)
# Move camera to follow ship
map_rect.x = the_ship.map_pos.x - map_rect.w/2
map_rect.y = the_ship.map_pos.y - map_rect.h/2
for s in moving:
# Display on screen sprites
if not map_rect.colliderect(s.map_rect):
s.remove(disp_sprites)
continue
s.add(disp_sprites)
if not win:
s.collide_ship(the_ship)
if len(gems) == 0:
win = True
### Display Logic ###
screen.fill(BLACK)
the_starfield.draw(screen, map_rect)
disp_sprites.update(map_rect=map_rect)
disp_sprites.draw(screen)
the_ship.update(rot_vector= the_ship.direction)
screen.blit(the_ship.image, the_ship.rect)
if not win:
elapsed_time = pg.time.get_ticks()/1000
elapsed_minutes = int(elapsed_time // 60)
elapsed_seconds = int(elapsed_time // 1) % 60
time_string = f"{elapsed_minutes:d}:{elapsed_seconds:02d}"
time_label = font.render(time_string, 1, WHITE)
time_pos = (screen.get_width()-10-time_label.get_width(),10)
screen.blit(time_label, time_pos)
if win:
gem_str = f"Level Complete!"
else:
gem_str = f"Gems to collect:{len(gems):3d} "
gem_label = font.render(gem_str,True, WHITE)
screen.blit(gem_label, (10, 10))
pg.display.flip()
clock.tick(MAX_FPS)
pg.quit()