Las modificaciones, con respecto al original del tutorial han sido:
Cambio de control con teclado a control con raton
Añadido sistema de puntuacion, asi como sistema de vidas(grafico)
Funcion reboot que "reinicia" el juego cada vez que te matan
Creacion de un Game Over
Implementacion de choques entre:la nave y los laseres enemigos(faltaba en el tutorial),entre los propios laseres y entre la nave buena y la mala
Ahi va el codigo:
- Código: Seleccionar todo
- """Space Invaders de StarWars
 Autor Original:dvl de la pagina linuxjuegos.com
 Modificaciones:Juan Guerrero(Yo)
 """
 import random,os,pygame
 from pygame.locals import *
 #Tamaño de pantalla
 SCREEN_WIDTH=800
 SCREEN_HEIGHT=600
 #Nombre de la carpeta con los archivos
 DATOS="datos"
 #Cargar Imagen#
 def load_image(name,colorkey=False):
 "asignamos la ruta de la carpeta donde guardaremos las imagenes"
 fullname=os.path.join(DATOS,name)
 try: image=pygame.image.load(fullname)
 except pygame.error,message:
 print 'No se puede cargar la imagen: ',fullname
 raise SystemExit,message
 image=image.convert()
 if (colorkey):
 colorkey=image.get_at((0,0))
 image.set_colorkey(colorkey,RLEACCEL)
 return image,image.get_rect()
 #Cargar Sonido#
 def load_SoundFile(name):
 class NoneSound:
 def play(self): pass
 if not pygame.mixer or not pygame.mixer.get_init():
 return NoneSound()
 fullname=os.path.join(DATOS,name)
 try:
 sound=pygame.mixer.Sound(fullname)
 except pygame.error,message:
 print'No se pudo cargar el sonido: ',fullname
 raise SystemExit,message
 
 return sound
 #Nave Buena#
 class XWing(pygame.sprite.Sprite):
 def __init__(self):
 pygame.sprite.Sprite.__init__(self)
 self.image,self.rect=load_image("xwing.bmp",True)
 "posicion inicial"
 self.rect.centerx=SCREEN_WIDTH
 self.rect.centery=(SCREEN_HEIGHT-40)
 
 def update(self):
 posicion=pygame.mouse.get_pos()
 self.rect.center=posicion
 """Evitamos salidas de pantalla
 restringimos el movimiento vertical a media pantalla
 """
 if self.rect.left<0:
 self.rect.left=0
 elif self.rect.right>SCREEN_WIDTH:
 self.rect.right=SCREEN_WIDTH
 if self.rect.top<=SCREEN_HEIGHT/2:
 self.rect.top=SCREEN_HEIGHT/2
 elif self.rect.bottom>=SCREEN_HEIGHT:
 self.rect.bottom=SCREEN_HEIGHT
 #Los Malos#
 class TIEFighter(pygame.sprite.Sprite):
 def __init__(self,startx):
 pygame.sprite.Sprite.__init__(self)
 self.image,self.rect=load_image("tie_fighter.bmp",True)
 self.rect.centerx=startx
 self.rect.centery=0
 self.x_velocity=random.randint(-5,5)
 self.y_velocity=random.randint(1,5)
 def update(self):
 self.rect.move_ip((self.x_velocity,self.y_velocity))
 
 if self.rect.left<=0:
 self.x_velocity=-(self.x_velocity)
 elif self.rect.right>=SCREEN_WIDTH:
 self.x_velocity=-(self.x_velocity)
 """Si se sale de pantalla, lo eliminamos para liberar
 espacio"""
 if self.rect.bottom>=SCREEN_HEIGHT:
 self.kill()
 "Disparos Aleatorios"
 fire=random.randint(1,60)
 if fire==1:
 tiefighterLaserSprites.add(TIEFighterLaser(self.rect.midbottom))
 tiefighterShotFX.play()
 #Laser de XWing#
 class XWingLaser(pygame.sprite.Sprite):
 def __init__(self,startpos):
 pygame.sprite.Sprite.__init__(self)
 self.image,self.rect=load_image("rebel_laser.bmp",True)
 self.rect.center=startpos
 def update(self):
 if self.rect.bottom<=0:
 self.kill()
 else:
 self.rect.move_ip((0,-4))
 #Laser de TIEFighter#
 class TIEFighterLaser(pygame.sprite.Sprite):
 def __init__(self,startpos):
 pygame.sprite.Sprite.__init__(self)
 self.image,self.rect=load_image("empire_laser.bmp",True)
 self.rect.midtop = startpos
 def update(self):
 """Si se sale de pantalla, lo eliminamos para liberar
 espacio"""
 if self.rect.bottom>=SCREEN_HEIGHT:
 self.kill()
 else:
 self.rect.move_ip((0,4))
 #puntaje#
 def puntuacion(puntos):
 puntos=puntos+1
 #vidas
 class corazon(pygame.sprite.Sprite):
 def __init__(self,posini):
 pygame.sprite.Sprite.__init__(self)
 self.image,self.rect=load_image("corazon.gif",True)
 self.rect.centerx=posini
 self.rect.centery=25
 
 """limpia la pantalla del juego cuando te matan"""
 def reboot(TIEFighterContainer):
 "Carga los 4 'malos' iniciales"
 TIEFighterContainer.add(TIEFighter(650))
 TIEFighterContainer.add(TIEFighter(50))
 TIEFighterContainer.add(TIEFighter(650))
 TIEFighterContainer.add(TIEFighter(50))
 return TIEFighterContainer
 
 def main():
 random.seed()
 pygame.init()
 screen=pygame.display.set_mode((SCREEN_WIDTH,SCREEN_HEIGHT),HWSURFACE|DOUBLEBUF)
 pygame.display.set_caption("STAR WARS INVADERS")
 "Limita el movimiento del raton a la pantalla de juego"
 pygame.event.set_grab(True)
 
 background_image,background_rect=load_image("background.bmp")
 screen.blit(background_image,(0,0))
 "Imagen de final de juego"
 gameover_image,gameover_rect=load_image("Vader.bmp")
 "Cargamos los sonidos"
 explode1FX=load_SoundFile("explode1.wav")
 global tiefighterShotFX
 tiefighterShotFX=load_SoundFile("empire_laser.wav")
 xwingShotFX=load_SoundFile("rebel_laser.wav")
 explode2FX=load_SoundFile("explode2.wav")
 risamalvadaFX=load_SoundFile("risa.mp3")
 #Creamos los containers
 xwingSprite=pygame.sprite.RenderClear()
 xwing=XWing()
 xwingSprite.add(xwing)
 xwingLaserSprites=pygame.sprite.RenderClear()
 #4 malos iniciales
 tiefighterSprites=pygame.sprite.RenderClear()
 reboot(tiefighterSprites)
 global tiefighterLaserSprites
 
 tiefighterLaserSprites=pygame.sprite.RenderClear()
 "Variable para bucle principal"
 running=True
 "Contador para aparicion de nuevos enemigos"
 addTieFighterCounter=0
 clock=pygame.time.Clock()
 gameover=False
 puntos=0
 nivel=0
 pygame.mouse.set_visible(False)
 #creamos las vidas
 vidas=pygame.sprite.RenderClear()
 vida3=corazon(30)
 vida2=corazon(70)
 vida1=corazon(110)
 vidas.add(vida1)
 vidas.add(vida2)
 vidas.add(vida3)
 
 #numero inicial de vidas
 nvidas=3
 #Fuente para el texto
 fuente=pygame.font.Font(None,40)
 while running is True:
 
 clock.tick(60)
 "Comprobamos si se produce algun evento de entrada"
 for event in pygame.event.get():
 if event.type == QUIT:
 running = False # Se acaba el juego
 elif event.type == KEYDOWN:
 if event.key == K_ESCAPE:
 running = False # Se acaba el juego
 "Dispara un laser cuando pulsemos la barra espaciadora"
 elif event.key == K_SPACE:
 xwingLaserSprites.add(XWingLaser(xwing.rect.midtop))
 xwingShotFX.play()
 """Creamos un laser a cada lado de la nave
 pulsando el boton izq del raton"""
 elif event.type == MOUSEBUTTONDOWN:
 xwingLaserSprites.add(XWingLaser(xwing.rect.midleft))
 xwingLaserSprites.add(XWingLaser(xwing.rect.midright))
 xwingShotFX.play()
 "Ajustamos el nivel"
 if puntos>=5:
 nivel+=1
 puntos=0
 "Incrementamos el contador para crear nuevos enemigos"
 addTieFighterCounter+=1
 if addTieFighterCounter>=(100-15*nivel):"Cada nivel apareceran mas rapido"
 tiefighterSprites.add(TIEFighter(random.randint(100,700)))
 addTieFighterCounter=0
 "Actualizamos los containers"
 xwingSprite.update()
 xwingLaserSprites.update()
 tiefighterSprites.update()
 tiefighterLaserSprites.update()
 """Comprobamos si ha habido choques
 Las diferentes posibilidades son:
 Malo vs LaserBueno
 Bueno vs LaserMalo
 Bueno vs Malo
 LaserBueno vs LaserMalo
 
 """
 for hit in pygame.sprite.groupcollide(tiefighterSprites,xwingLaserSprites,1,1):
 explode1FX.play()
 puntos+=1
 for hit in pygame.sprite.groupcollide(xwingSprite,tiefighterLaserSprites,0,1):
 explode2FX.play()
 "Vamos eliminando los corazones en pantalla y restando vidas"
 if nvidas==3:
 vidas.remove(vida1)
 elif nvidas==2:
 vidas.remove(vida2)
 else:
 vidas.remove(vida3)
 nvidas-=1
 if nvidas==0:
 gameover=True
 else:
 "Vaciamos todos los containers y limpiamos la pantalla"
 tiefighterLaserSprites.empty()
 tiefighterSprites.empty()
 pygame.mouse.set_pos((SCREEN_WIDTH/2),SCREEN_HEIGHT-40)
 xwingLaserSprites.empty()
 tiefighterLaserSprites.clear(screen,background_image)
 tiefighterSprites.clear(screen,background_image)
 xwingSprite.clear(screen,background_image)
 xwingLaserSprites.clear(screen,background_image)
 vidas.clear(screen,background_image)
 fuente=pygame.font.Font(None,40)
 Puntaje=fuente.render(str(puntos),1,(255,255,255))
 Nivel=fuente.render(str(nivel),1,(255,255,255))
 screen.blit(background_image,(0,0))
 screen.blit(Puntaje,(SCREEN_WIDTH/2,0))
 screen.blit(Nivel,(SCREEN_WIDTH/2+20,0))
 tiefighterLaserSprites.draw(screen)
 xwingLaserSprites.draw(screen)
 xwingSprite.draw(screen)
 tiefighterSprites.draw(screen)
 vidas.draw(screen)
 "Establecemos un tiempo de espera antes de reiniciar"
 pygame.time.wait(800)
 "reiniciamos con los 4 malos del comienzo
 reboot(tiefighterSprites)
 """Este caso es igual que el anterior, solo que en esta ocasion se trata
 de choques entre naves"""
 for hit in pygame.sprite.groupcollide(xwingSprite,tiefighterSprites,0,1):
 explode2FX.play()
 explode1FX.play()
 if nvidas==3:
 vidas.remove(vida1)
 elif nvidas==2:
 vidas.remove(vida2)
 else:
 vidas.remove(vida3)
 nvidas-=1
 if nvidas==0:
 gameover=True
 else:
 tiefighterLaserSprites.empty()
 tiefighterSprites.empty()
 pygame.mouse.set_pos((SCREEN_WIDTH/2),10)
 xwingLaserSprites.empty()
 tiefighterLaserSprites.clear(screen,background_image)
 tiefighterSprites.clear(screen,background_image)
 xwingSprite.clear(screen,background_image)
 xwingLaserSprites.clear(screen,background_image)
 vidas.clear(screen,background_image)
 fuente=pygame.font.Font(None,40)
 Puntaje=fuente.render(str(puntos),1,(255,255,255))
 Nivel=fuente.render(str(nivel),1,(255,255,255))
 screen.blit(background_image,(0,0))
 screen.blit(Puntaje,(SCREEN_WIDTH/2,0))
 screen.blit(Nivel,(SCREEN_WIDTH/2+20,0))
 tiefighterLaserSprites.draw(screen)
 xwingLaserSprites.draw(screen)
 xwingSprite.draw(screen)
 tiefighterSprites.draw(screen)
 vidas.draw(screen)
 
 pygame.time.wait(800)
 
 reboot(tiefighterSprites)
 for hit in pygame.sprite.groupcollide(xwingLaserSprites,tiefighterLaserSprites,1,1):
 explode1FX.play()
 
 if gameover: pygame.time.delay(1000)
 "Borramos y pintamos los elementos de la pantalla"
 tiefighterLaserSprites.clear(screen,background_image)
 tiefighterSprites.clear(screen,background_image)
 xwingSprite.clear(screen,background_image)
 xwingLaserSprites.clear(screen,background_image)
 vidas.clear(screen,background_image)
 fuente=pygame.font.Font(None,40)
 Puntaje=fuente.render(str(puntos),1,(255,255,255))
 Nivel=fuente.render(str(nivel),1,(255,255,255))
 screen.blit(background_image,(0,0))
 screen.blit(Puntaje,(SCREEN_WIDTH/2,0))
 screen.blit(Nivel,(SCREEN_WIDTH/2+20,0))
 tiefighterLaserSprites.draw(screen)
 xwingLaserSprites.draw(screen)
 xwingSprite.draw(screen)
 tiefighterSprites.draw(screen)
 vidas.draw(screen)
 
 pygame.display.flip()
 "Final de juego"
 if gameover:
 screen.blit(gameover_image,(0,0))
 pygame.display.flip()
 risamalvadaFX.play()
 running=False
 pygame.event.set_grab(False)
 if __name__=='__main__':
 main()
 
Como podreis comprobar, este juego tiene una serie de mejoras posibles:
creacion de una funcion que se encargue de la actualizacion(puesto que llegamos a repetir el mismo codigo tres veces), el hecho de que a partir de cierto nivel, el tiempo de aparicion entre malo y malo es cero(para esto se podria añadir que cada cinco niveles, apareciera un malo malisimo,en plan estrealla de la muerte, y el tiempo entre malo y malo se restableciera)
Otro fallo que no entiendo es el hecho d que el sonido de la risa malvada no suena,alguien sabe por que??
Espero comentarios y criticas




 
 



