• Revista PROGRAMAR: Já está disponível a edição #53 da revista programar. Faz já o download aqui!

rolando2424

[Python] [Pyteam] Tutorial de Pygame

18 mensagens neste tópico

Neste tutorial, vamos ver como colocar um circulo no ecrã, e movê-lo usando as setas do teclado.

No final deverão ter algo assim parecido (Não se preocupem se não entenderem alguma coisa, pois o

código vai ser analisado linha a linha):

#!/usr/bin/env python

import pygame
from pygame.locals import *

if not pygame.font:
    print 'Atenção, não existem fontes.'

if not pygame.mixer:
    print 'Atenção, não existe som.'

pygame.init()


vermelho = (255, 0, 0)
preto = (0, 0, 0)


comprimento_ecra = 640
altura_ecra = 480

ecra = pygame.display.set_mode((comprimento_ecra, altura_ecra))


raio_circulo = 10

xpos = 50
ypos = 50

circulo = pygame.draw.circle(ecra, vermelho, (xpos, ypos), raio_circulo)

movimento_em_x = 5
movimento_em_y = 5

pygame.display.flip()

pygame.key.set_repeat(100, 100)

while True:
    for event in pygame.event.get():
        pass

    tecla_pressionada = pygame.key.get_pressed()

    if tecla_pressionada[K_LEFT]:
        xpos -= movimento_em_x

    if tecla_pressionada[K_RIGHT]:
        xpos += movimento_em_x


    if tecla_pressionada[K_UP]:
        ypos -= movimento_em_y

    if tecla_pressionada[K_DOWN]:
        ypos += movimento_em_y

    ecra.fill(preto)
    circulo = pygame.draw.circle(ecra, vermelho, (xpos, ypos), raio_circulo)
    pygame.display.flip()

#!/usr/bin/env python

Esta linha é só para o pessoal que usa Linux, e serve para mostrar onde se encontra o executável do

Python. Existem duas versões para esta linha. o "#!/usr/bin/env python" e o "#!/usr/bin/python". Esta

linha tem de ser a primeira do ficheiro (neste caso, whitespace conta). Existem algumas diferenças entre

as duas, mas são irrelevantes numa base diária, e não são apropriadas para este tutorial.

Bem, após este aparte (e foi um aparte grande), vamos ao que interessa:

import pygame
from pygame.locals import *

O Pygame é um módulo para o Python (parto do principio que já o têm instalado, caso contrário devem de o

encontrar nos repositórios da vossa distro de Linux, ou então dirigem-se para o site oficial em

http://www.pygame.org/download.shtml onde podem encontrar ports para o Windows e Mac, ou então as

sources, caso queiram compilar vocês mesmos).

Sendo o Pygame um módulo, é necessário importa-lo, usando o comando "import pygame".

O pygame.locals contêm coisas como as teclas do teclado, e para ser mais rápido aceder-mos a elas,

importamos o módulo directamente.

if not pygame.font:   
    print 'Atenção, não existem fontes.'
    
if not pygame.mixer:
    print 'Atenção, não existe som.'

Estes dois blocos são opcionais, mas dá sempre jeito usar. Caso o programa não consiga carregar as

fontes do pygame, ou não consiga aceder ao som, ele imprime uma mensagem de erro na consola.

pygame.init()

Este comando inicia todos os módulos que são importados quando se usa o "import pygame". Se quiserem, é

possível iniciar os módulos um a um, mas normalmente, tal não é necessário. Se tiverem a usar um

interpreter como o IDLE, deverão de receber uma tuple, que vos indica os módulos que foram iniciados com

sucesso, e os que não foram iniciados. (Em condições normais, este comando deve de fazer um return de

(6, 0), ou seja, 6 módulos iniciados correctamente, e 0 não iniciados).

vermelho = (255, 0, 0)
preto = (0, 0, 0)

Acho que quando se está num tutorial, não deve de aparecer conjuntos de números assim do nada, por isso

crio variáveis para as cores que vão ser usadas. O vermelho, vai ser a cor da bola, e o preto vai ser a

cor que vamos usar para limpar o ecrã no fim de cada frame (ja explico isso). As cores são dadas no

formato RGB, ou seja, Vermelho, Verde e Azul, sendo que também têm que ser dadas numa tuple. Logo,

(255, 0, 0), é o vermelho mais forte, e o (0, 0, 0) é o preto (ausência de cor vermelha, verde e azul).

comprimento_ecra = 640
altura_ecra = 480

Tal como em cima, não gosto de por números mágicos, que parecem aparecer (digam isto muito depressa :P)

do nada, por isso, estão aqui definidas o tamanho do ecrã do pygame. Neste caso, a janela resultante

terá uma resolução de 640x480. Caso queiram mudar o tamanho da janela, é só mudar os valores. Simples :)

ecra = pygame.display.set_mode((comprimento_ecra, altura_ecra))

Esta linha cria uma janela, de tamanho 640x480 (por causa das variaveis que criamos acima). Reparem que

têm que dar uma tuple de dois membros para criar a janela ( ou seja, ecra =

pygame.display.set_mode(comprimento_ecra, altura_ecra) não dava (reparem nos dois parênteses acima)).

raio_circulo = 10

xpos = 50
ypos = 50

A variável raio_circulo vai definir o raio do círculo em pixeis (podiam não ter reparado nisso :) ).

As variáveis xpos e ypos vão definir a posição onde o círculo vai aparecer na primeira

frame.

circulo = pygame.draw.circle(ecra, vermelho, (xpos, ypos), raio_circulo)

Agora vamos criar o circulo, usando o módulo draw do pygame. Assim podemos criar as

imagens, sem termos

que usar sprites criadas noutros programas (é claro que o draw só faz figuras básicas como as figuras

geométricas). O draw pode criar também, por exemplo, rectângulos. Para verem tudo o que ele pode criar,

vão à documentação oficial sobre o módulo, que pode ser encontrada aqui.

Em relação ao pygame.draw.circle, ele requer os seguintes argumentos: o nome da variável da janela onde

ele irá desenhar o círculo, a cor que o círculo deverá ter, uma tuple com a posição do centro do

círculo (x, y), e o raio que o círculo deverá ter.

Ou seja, este círculo será criado na nossa janela, com a cor vermelha, na posição (50, 50) (por causa

das variáveis que definimos atrás), com um raio de 10.

movimento_em_x = 5
movimento_em_y = 5   

Isto vai servir para definir o número de pixels que o círculo se vai mover, no eixo dos "x" e no eixo

dos "y" (Isto vai ser visto mais à frente).

pygame.display.flip()

Este comando faz com que o Pygame actualize todo a janela, ou seja, caso haja algum tipo de movimento,

este comando "cola" tudo no ecrã para nos vermos. (Ou seja, mesmo que movimentem o círculo, nunca verão

o resultado, se não usarem o flip() (por acaso também existe outra maneira, mas é mais complicado :) )).

pygame.key.set_repeat(1000, 100)

Em condições normais, o Pygame não "aceita" um tecla pressionada, como uma repetição. Ou seja, se

pressionarem a seta para a esquerda, e deixarem lá estar o dedo, ele só irá mover o círculo para a

esquerda uma vez. Para fazer com que ele voltasse a mover o círculo para a esquerda, tínhamos que

levantar o dedo da tecla, e depois voltar a pressionar. Para combater isso, usámos o "set_repeat".

O primeiro valor, é o tempo que temos de deixar o dedo na tecla, até o Pygame aceitar a primeira

repetição, e o segundo valor, é o tempo de intervalo que existe entre cada repetição. Todos os valores

são dados em milissegundos (ou seja, 1000 neste caso é um segundo). Neste exemplo, quando carregarem

para a esquerda, e deixarem lá estar o dedo, o círculo irá mover-se para a esquerda 5 pixels, depois irá

parar durante um segundo, e depois começará a mover-se a 5 pixels por 100 milésimos de segundo (ou 50

pixels por segundo). Isto é um pouco complicado de explicar por escrito, o melhor é mesmo modificarem os

valores, e verem como afecta o programa.

while True:

Tudo o que é jogo, tem de ter um main loop, para poder processar o input durante as frames.

    for evento in pygame.event.get():
        pass

O modulo "event" do pygame é o que trata de todos os eventos que ocorrem. A função get() faz return de

uma lista, com tudo o que se passa num determinado momento (para experimentarem, tentem trocar o "pass"

por "print evento"). Como uma lista dessas ocupa muito espaço na memória se deixada a correr durante

muito tempo, o melhor é ir limpando-a com o "pass" (para ela não ficar na memória).

    tecla_pressionada = pygame.key.get_pressed()

Esta variável, vai armazenar as teclas que são carregadas, para depois comparar com os "if"s que temos À

frente, e caso encontre a tecla que pressionamos num "if", ele executa o bloco.

    if tecla_pressionada[K_LEFT]:
        xpos -= movimento_em_x

Caso a tecla que carregamos seja a seta esquerda (lembrem-se que ela deriva do pygame.locals, que

importamos separadamente), modificamos a posição do círculo (lembrem-se que a posição do círculo é dada

pelo conjunto (xpox, ypos).

Como a "grelha" é do tipo:

    y^

      |

      |

      |

  --------->

      |0  x

      |

      |

Para fazer-mos o círculo andar para a esquerda, temos que subtrair ao valor de x, para o fazer andar

para a direita, somar ao valor de x, para fazer andar para cima, adicionar ao valor de y, e para fazer

andar para baixo, subtrair ao valor de y.

E é isso que os próximo blocos fazem o mesmo que este, excepto que mudam os eixos e as teclas a

carregar.

    if tecla_pressionada[K_RIGHT]:
        xpos += movimento_em_x


    if tecla_pressionada[K_UP]:
        ypos -= movimento_em_y

    if tecla_pressionada[K_DOWN]:
        ypos += movimento_em_y

Agora que o programa já sabe a posição que o círculo vai tomar, está na hora de o colocar no ecrã.

    screen.fill(black)

No entanto, antes de colocar o círculo no ecrã, temos que voltar a preencher o background da janela,

para apagar o círculo anterior (senão vão ficar com "rastos" do caminho por onde o círculo percorre. Se

quiserem, apaguem esta linha e corram o programa outra vez, para verem o efeito).

Nós não tivemos que fazer isto ao início, porque a cor da janela já é o preto por default.

    circulo = pygame.draw.circle(ecra, vermelho, (xpos, ypos), raio_circulo)

Agora que a janela já foi limpa do círculo que estava antes, está na hora de desenhar o círculo na sua

nova posição (a única coisa que mudou foi o par (xpos, ypos) ).

    pygame.display.flip()

No entanto, para fazer o círculo aparecer na janela, temos que a actualizar e como vimos antes, isso é

feito usando o pygame.display.flip()

E já está, agora devem de ter um programa que vos permite mexer uma bola numa janela preta (Ok, não é o

Unreal 2007 ou o Starcraft 2, mas todos temos de começar em algum lado certo?).

Agora podem modificar o código, para obterem vários efeitos (mudem a cor de fundo, o tamanho da janela,

a cor, o tamanho do círculo, etc.)

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Eu que não conheço (ainda) Python, achei um tutorial altamente. Mesmo o código parece-me simples.

Parabéns! Cumprimentos

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Fico feliz por teres gostado, Python é uma linguagem relativamente simples em termo de sintaxe, e lê-se o código facilmente :)

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Como faço pra correr um ficheiro Py em Windows?

EDIT: Pergunta estúpida.. lol. Já descobri

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites
Traceback (most recent call last):
  File "apps\pygame.txt", line 39, in <module>
    while executar:
NameError: name 'executar' is not defined

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Antes do while executar:, mete executar = True ou troca o executar por True. :D

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Traceback (most recent call last):
  File "apps\pygame.txt", line 39, in <module>
    while executar:
NameError: name 'executar' is not defined

É que eu fui fazendo alterações ao código enquanto ia escrevendo o tuturial (se repares, mais abaixo, na explicação tem "while True:" em vez de "while executar:").

Faz aquilo que o djthyrax disse ou troca o "while executar" por "while True:"

Vou corrigir o código.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites
Traceback (most recent call last):
  File "apps\pygame.txt", line 58, in <module>
    screen.fill(black)
NameError: name 'screen' is not defined

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Traceback (most recent call last):
  File "apps\pygame.txt", line 58, in <module>
    screen.fill(black)
NameError: name 'screen' is not defined

Altera a linha screen.fill(black) para ecra.fill(black).

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Traceback (most recent call last):
  File "apps\pygame.txt", line 58, in <module>
    screen.fill(black)
NameError: name 'screen' is not defined

Altera a linha screen.fill(black) para ecra.fill(black).

Pois, mais uma vez, é no que dá fazer alteração a um ficheiro depois de fazer a verificação do código ;)

Vou alterar no primeiro post.

EDIT: Prontos, agora tenho a certeza que irá dar (esqueci-me também que tinha mudado de black para preto ;))

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

pessoal, tava a fazer este tutorial, mt bom...só ke dá-m este erro ao fazer o loop:

>>>while True:

. . .  for event in pygame.event.get( ):

  File "<stdin>", line 2

        for event in pygame.event.get( ):

IndentationError: expected an indented block

Eu tou a utilizar Linux e a versao do python e a 2.5.1

Será k me podiam ajudar?

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

pessoal, tava a fazer este tutorial, mt bom...só ke dá-m este erro ao fazer o loop:

>>>while True:

. . .  for event in pygame.event.get( ):

  File "<stdin>", line 2

        for event in pygame.event.get( ):

IndentationError: expected an indented block

Eu tou a utilizar Linux e a versao do python e a 2.5.1

Será k me podiam ajudar?

Tens que carregar no butão TAB para fazeres um indent (colocar o texto "mais para dentro")

E aconselho-te a usares o IDLE, que é estilo a shell em texto do python, mas melhor (dá-te algumas ajudas, como fazer-te o indent automaticamente, etc.)

Se estás a usar o Ubuntu, faz um "sudo apt-get install idle2.5" (se a memória não me engana).

Caso não dê, faz um "apt-cache search idle python" e vê qual é o nome certo :D

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Brigadão por este Tutorial, mt bom msm! Agora vou ver se brinko com isto para dps avançar mais na matéria :D

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Ora viva... vi este tutorial no wiki e estive a le-lo.

Não há nada de mal com este tutorial da forma como foi feito, tem lugar aqui no fórum, no entanto para ser afixado no wiki precisa de muita coisa a ser mudada.

Está um documento engraçado e dá pra quem não conhece ter um cheirinho de python, mas está demasiado informal para estar no wiki.

Os problemas que lhe aponto são estes:

-está escrito na primeira pessoa (isto não é crítico)

-não é um tutorial, é apenas um exemplo do que o pygame pode fazer, este é o problema maior

-explica coisas como shebang line ou como importar módulos. Isso não é relevante, quem quiser aventurar-se pelo pygame terá que ter um mínimo de conhecimento da linguagem python

provavelmente desaparecerá do wiki enqunato tutorial, em principio ficará apenas o código que terá que ser revisto.

Por exemplo não sao precisos testes de dependencias nem é preciso definir as variáveis previamente. Estamos a falar de código cons fins didáticos e não de um programa com uma base de código grande e/ou que será distribuido.

Alguma opinião em relação a isto digam aí.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Por exemplo não sao precisos testes de dependencias nem é preciso definir as variáveis previamente. Estamos a falar de código cons fins didáticos e não de um programa com uma base de código grande e/ou que será distribuido.

Alguma opinião em relação a isto digam aí.

Acho sempre boa prática fazer testes de dependências.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Acho sempre boa prática fazer testes de dependências.

Não está em causa ser boa pratica ou não, é um padrão que tem a sua utilidade e deve ser usado quando é preciso por quem precisa.  O que está em causa é a utilidade de explicar isso num tutorial do pygame, que é pouca.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Crie uma conta ou ligue-se para comentar

Só membros podem comentar

Criar nova conta

Registe para ter uma conta na nossa comunidade. É fácil!


Registar nova conta

Entra

Já tem conta? Inicie sessão aqui.


Entrar Agora