I am working on a game that features randomly generated caves. It starts by creating a 640x480 field of 16x16 blocks. Then 3 instances of CaveMaker
are placed, and these destroy every block they touch, they are supposed to shift direction every few seconds to result in random cave like pathways, but with my code, they turn up like this rubbish:
And I believe it is because the very improvised code I wrote that is supposed to make it change direction:
class CaveMaker(object):
def __init__(self):
self.active=1
self.x=randrange(1,640)
self.y=randrange(1,480)
#Choose a X speed and Y speed
self.direction=(choice([20,-20,1,-1,15,0,-15]),choice([20,-20,1,-1,15,0,-15]))
self.rect=pygame.Rect(self.x,self.y,75,75)
#Set amount of time to move this direction
self.timeout=choice([30,50,70,90,110])
self.destroytime=randrange(200,360)
def Update(self):
if self.active==1:
#Move in a certain direction?
self.x+=self.direction[0]
self.y+=self.direction[1]
self.timeout-=1
if self.timeout==0:
#Change direction?
self.direction= (choice([20,-20,1,-1,15,0,-15]),choice([20,-20,1,-1,15,0,-15]))
self.timeout=choice([30,50,70,90,110])
self.destroytime-=1
if self.destroytime==0:
self.active=0
self.rect=pygame.Rect(self.x,self.y,60,60)
So how do I tell the object to move random directions?
Here is my full code:
import pygame
from pygame.locals import *
from collections import namedtuple
from random import randrange,choice
pygame.init()
screen=pygame.display.set_mode((640,480))
Move = namedtuple('Move', ['up', 'left', 'right'])
max_gravity=50
class Block(object):
def __init__(self,x,y):
self.x=x
self.y=y
self.rect=pygame.Rect(self.x,self.y,16,16)
class CaveMaker(object):
def __init__(self):
self.active=1
self.x=randrange(1,640)
self.y=randrange(1,480)
#Choose a X speed and Y speed
self.direction=(choice([20,-20,1,-1,15,0,-15]),choice([20,-20,1,-1,15,0,-15]))
self.rect=pygame.Rect(self.x,self.y,75,75)
#Set amount of time to move this direction
self.timeout=choice([30,50,70,90,110])
self.destroytime=randrange(200,360)
def Update(self):
if self.active==1:
#Move in a certain direction?
self.x+=self.direction[0]
self.y+=self.direction[1]
self.timeout-=1
if self.timeout==0:
#Change direction?
self.direction=(choice([20,-20,1,-1,15,0,-15]),choice([20,-20,1,-1,15,0,-15]))
self.timeout=choice([30,50,70,90,110])
self.destroytime-=1
if self.destroytime==0:
self.active=0
self.rect=pygame.Rect(self.x,self.y,60,60)
class Player(object):
def __init__(self, x, y):
self.rect = pygame.Rect(x,y,16,16)
self.on_ground = True
self.xvel = 0
self.yvel = 0
self.jump_speed = 5
self.move_speed = 2
def update(self, move, blocks):
if move.up and self.on_ground:
self.yvel -= self.jump_speed
if move.left:
self.xvel = -self.move_speed
if move.right:
self.xvel = self.move_speed
if not self.on_ground:
self.yvel += 0.3
if self.yvel > max_gravity: self.yvel = max_gravity
if not (move.left or move.right):
self.xvel = 0
self.rect.left += self.xvel
self.collide(self.xvel, 0, blocks)
self.rect.top += self.yvel
self.on_ground = False;
self.collide(0, self.yvel, blocks)
def collide(self, xvel, yvel, blocks):
for block in [blocks[i] for i in self.rect.collidelistall(blocks)]:
if xvel > 0:
self.rect.right = block.rect.left
if xvel < 0:
self.rect.left = block.rect.right
if yvel > 0:
self.rect.bottom = block.rect.top
self.on_ground = True
self.yvel = 0
if yvel < 0: self.rect.top = block.rect.bottom;self.yvel=0
blocks=[]
cavemakes=[]
gen=1
genx=0
geny=0
px=0
py=0
cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());
while True:
key=pygame.key.get_pressed()
if gen==1:
blocks.append(Block(genx,geny))
geny+=16
if geny>480:
geny=0
genx+=16
if genx>640:
gen=2
elif gen==2:
screen.fill((5,80,200))
for b in blocks:
pygame.draw.rect(screen, (90,90,90), b.rect, 0)
for c in cavemakes:
if c.active==0:
gen='done'
while any(b.rect.collidepoint(px, py) for b in blocks):
px=randrange(1,630)
py=randrange(1,470)
player=Player(px,py)
c.Update()
for b in blocks:
if b.rect.colliderect(c.rect):
blocks.remove(b)
pygame.display.flip()
if gen=='done':
screen.fill((5,80,200))
for b in blocks:
pygame.draw.rect(screen, (90,90,90), b.rect, 0)
for e in pygame.event.get():
if e.type==KEYUP:
if e.key==K_r:
blocks=[]
cavemakes=[]
gen=1
genx=0
geny=0
px=0
py=0
cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());cavemakes.append(CaveMaker());
if e.type==QUIT:
exit()
move = Move(key[K_w], key[K_a], key[K_d])
player.update(move,blocks)
pygame.draw.rect(screen, (5,200,5), player.rect, 3)
pygame.display.flip()