Introducción a Pygame Zero

Creación de una ventana

Primero, crea un archivo vacío llamado intro.py.

Comprueba que se ejecuta y crea una ventana en blanco ejecutando:

pgzrun intro.py

Todo en Pygame Zero es opcional; ¡un archivo en blanco es un script válido de Pygame Zero!

Puedes salir del juego haciendo clic en el botón de cierre de la ventana o pulsando Ctrl-Q (⌘-Q en Mac). Si el juego deja de responder por alguna razón, puedes terminarlo pulsando Ctrl-C en tu ventana de Terminal.

Dibujar un fondo

A continuación, vamos a añadir una función draw() y establecer las dimensiones de la ventana. Pygame Zero llamará a esta función cada vez que necesite pintar la pantalla.

En intro.py, añade lo siguiente:

1
2
3
4
5
WIDTH = 300
HEIGHT = 300

def draw():
    screen.fill((128, 0, 0))

Vuelve a ejecutar pgzrun intro.py y la pantalla debería ser ahora un cuadrado rojizo.

¿Qué hace este código?

WIDTH y HEIGHT controlan la anchura y la altura de tu ventana. El código establece que el tamaño de la ventana sea de 300 píxeles en cada dimensión.

screen es un built-in que representa la pantalla de la ventana. Tiene una gama de métodos para dibujar sprites y formas. La llamada al método screen.fill() rellena la pantalla con un color sólido, especificado como una tupla de colores (red, green, blue). El color (128, 0, 0) será un rojo medio-oscuro. Pruebe a cambiar estos valores con números entre 0 y 255 y vea qué colores puede crear. También puedes usar una cadena para nombrar un nombre de color incorporado.

Vamos a crear un sprite que podamos animar.

Dibujar un sprite

Antes de que podamos dibujar nada, necesitaremos guardar un sprite alienígena para usarlo. Puedes hacer clic con el botón derecho sobre éste y guardarlo («Guardar imagen como…» o similar).

_images/alien.png

(Este sprite tiene un canal de transparencia (o «alfa»), ¡lo cual es genial para los juegos! Pero está diseñado para un fondo oscuro, por lo que es posible que no puedas ver el casco espacial del alienígena hasta que se muestre en el juego).

Truco

Puedes encontrar muchos sprites gratuitos, incluido éste, en kenney.nl. Éste procede del paquete Platformer Art Deluxe pack.

Tienes que guardar el archivo en el lugar correcto para que Pygame Zero pueda encontrarlo. Crea un directorio llamado images y guarda la imagen en él como alien.png. Ambos deben estar en minúsculas. Pygame Zero se quejará de lo contrario, para alertarte de un posible problema de compatibilidad entre plataformas.

Si has hecho esto, tu proyecto debería tener este aspecto:

.
├── images/
│   └── alien.png
└── intro.py

images/ es el directorio estándar en el que Pygame Zero buscará tus imágenes.

Hay una clase incorporada llamada Actor que puedes usar para representar un gráfico que se dibujará en la pantalla.

Vamos a definir uno ahora. Cambia el archivo intro.py para que diga:

1
2
3
4
5
6
7
8
9
alien = Actor('alien')
alien.pos = 100, 56

WIDTH = 500
HEIGHT = alien.height + 20

def draw():
    screen.clear()
    alien.draw()

¡Tu alienígena debería aparecer ahora en la pantalla! Al pasar la cadena alien a la clase Actor, ésta carga automáticamente el sprite, y tiene atributos como el posicionamiento y las dimensiones. Esto nos permite establecer la Altura (HEIGHT) de la ventana en función de la altura del alienígena.

El método alien.draw() dibuja el sprite en la pantalla en su posición actual.

Mover el alienígena

Vamos a poner el alien fuera de la pantalla; cambia la línea alien.pos para que diga:

alien.topright = 0, 10

Observa cómo puedes asignar a topright para mover al actor alienígena por su esquina superior derecha. Si el borde derecho del alienígena está en 0, el alienígena está justo fuera de la pantalla hacia la izquierda. Ahora vamos a hacer que se mueva. Añade el siguiente código al final del archivo:

def update():
    alien.left += 2
    if alien.left > WIDTH:
        alien.right = 0

Pygame Zero llamará a su función update() una vez cada fotograma. Mover el alienígena un pequeño número de píxeles cada fotograma hará que se deslice por la pantalla. Una vez que se deslice por el lado derecho de la pantalla, lo volvemos a poner a la izquierda.

Sus funciones draw() y update() trabajan de forma similar pero están diseñadas para dos propósitos diferentes. La función draw() dibuja la posición actual del alienígena mientras que la función update() se utiliza para mostrar al alienígena moviéndose en la pantalla.

Manejo de los clics

Hagamos que el juego haga algo cuando se hace clic en el alienígena. Para ello necesitamos definir una función llamada on_mouse_down(). Añade esto al código fuente:

1
2
3
4
5
def on_mouse_down(pos):
    if alien.collidepoint(pos):
        print("¡Eek!")
    else:
        print("¡No me has pillado!")

Deberías ejecutar el juego y probar a pulsar sobre el alienígena y a sacarlo de él.

Pygame Zero es inteligente sobre cómo llama a sus funciones. Si no defines tu función para que tome un parámetro pos, Pygame Zero la llamará sin una posición. También hay un parámetro button para on_mouse_down. Así que podríamos haber escrito:

def on_mouse_down():
    print("¡Has hecho clic!")

o:

def on_mouse_down(pos, button):
    if button == mouse.LEFT and alien.collidepoint(pos):
        print("¡Eek!")

Sonidos e imágenes

Ahora vamos a hacer que el alienígena aparezca herido. Guarda estos archivos:

  • alien_hurt.png - guarda esto como alien_hurt.png en el directorio images.

  • eep.wav - crear un directorio llamado sounds y guardar esto como eep.wav en ese directorio.

Tu proyecto debería tener ahora este aspecto:

1
2
3
4
5
6
7
.
├── images/
│   └── alien.png
│   └── alien_hurt.png
├── sounds/
│   └── eep.wav
└── intro.py

sounds/ es el directorio estándar que Pygame Zero buscará para encontrar tus archivos de sonido.

Ahora vamos a cambiar la función on_mouse_down para que utilice estos nuevos recursos:

def on_mouse_down(pos):
    if alien.collidepoint(pos):
        alien.image = 'alien_hurt'
        sounds.eep.play()

Ahora, cuando hagas clic en el alienígena, deberías escuchar un sonido, y el sprite cambiará a un alienígena infeliz.

Sin embargo, hay un error en este juego; el alienígena no vuelve a cambiar a un alienígena feliz (pero el sonido se reproducirá en cada clic). Vamos a arreglar esto a continuación.

Reloj

Si estás familiarizado con Python fuera de la programación de juegos, puede que conozcas el método time.sleep() que inserta un retraso. Podrías estar tentado a escribir código como este:

1
2
3
4
5
6
def on_mouse_down(pos):
    if alien.collidepoint(pos):
        alien.image = 'alien_hurt'
        sounds.eep.play()
        time.sleep(1)
        alien.image = 'alien'

Por desgracia, esto no es en absoluto adecuado para su uso en un juego. time.sleep() bloquea toda la actividad; queremos que el juego siga corriendo y animando. De hecho, tenemos que volver de on_mouse_down, y dejar que el juego resuelva cuándo reiniciar al alienígena como parte de su procesamiento normal, todo mientras ejecuta sus métodos draw() y update().

Esto no es difícil con Pygame Zero, porque tiene una clase incorporada: Clock que puede programar funciones para ser llamadas más tarde.

Primero, vamos a «refactorizar» (es decir, reorganizar el código). Podemos crear funciones para establecer el alien como hurt y también para cambiarlo de nuevo a normal:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
def on_mouse_down(pos):
    if alien.collidepoint(pos):
        set_alien_hurt()


def set_alien_hurt():
    alien.image = 'alien_hurt'
    sounds.eep.play()


def set_alien_normal():
    alien.image = 'alien'

Esto no va a hacer nada diferente todavía. set_alien_normal() no será llamado. Pero vamos a cambiar set_alien_hurt() para que use el reloj, de forma que set_alien_normal() sea llamado un poco después.

def set_alien_hurt():
    alien.image = 'alien_hurt'
    sounds.eep.play()
    clock.schedule_unique(set_alien_normal, 0.5)

clock.schedule_unique() hará que set_alien_normal() sea llamado después de 0.5 segundos. schedule_unique() también evita que la misma función se programe más de una vez, como por ejemplo si haces clic muy rápidamente.

Pruébalo, y verás que el alienígena vuelve a la normalidad después de 0,5 segundos. Prueba a hacer clic rápidamente y comprueba que el alienígena no revierte hasta 0,5 segundos después del último clic.

clock.schedule_unique() acepta tanto números enteros como flotantes para el intervalo de tiempo. En el tutorial estamos usando un número float para mostrar esto pero siéntete libre de usar ambos para ver la diferencia y los efectos que tienen los diferentes valores.

Resumen

Hemos visto cómo cargar y dibujar sprites, reproducir sonidos, manejar eventos de entrada y utilizar el reloj incorporado.

Tal vez quieras ampliar el juego para llevar la puntuación, o hacer que el alienígena se mueva de forma más errática.

Hay muchas más características incorporadas para que Pygame Zero sea fácil de usar. Consulta el Objetos incorporados para aprender a utilizar el resto de la API.