2009-09-12 59 views
4

这里是我如何实现我的简单pygames现在:这个基本的pygame结构如何?

import pygame, sys 
from pygame.locals import * 

def run_game(): 
    pygame.init() 

    SIZE = (640, 400) 
    BG_COLOUR = (0, 0, 0) 
    LINE_COLOUR = (255, 255, 255) 

    screen = pygame.display.set_mode(SIZE) 
    clock = pygame.time.Clock() 

    while True: 
     time_passed = clock.tick(30) 
     for event in pygame.event.get(): 
       if event.type == QUIT: 
         exit_game() 

     screen.fill(BG_COLOUR) 
     pygame.draw.aaline(screen, LINE_COLOUR, (1, 1), (639, 399)) 
     pygame.display.flip() 

def exit_game(): 
    sys.exit() 

if __name__ == "__main__" 
    run_game() 

我还看到一个keeprunning标志被用来退出主事件循环代替,以及使用pygame.event.poll()而不是通过pygame.event.get()循环。任何建议,如变量的情况/命名,任何使其更有效或可读的建议?

回答

12

无论pygame作者建议,我建议避免from ... import *:它不仅使你的代码难以阅读(如读者有检查每一个barename来检查它是否是实际在本地转让或来自厉害的*)。比如说,把它改成import pygame.locals as pygl,并且每一次使用它的名字都是合格的(我认为在你的代码中这意味着将QUIT更改为pygl.QUIT)。你选择什么简称代替pygl并不重要,但这是我强烈建议的一般结构。 Remeber:命名空间是个好主意 - 让我们来做更多这些!)

随处可用4格缩进,正如PEP 8所说的:您似乎将一些4格缩进与其他8格缩进混合,空间或标签 - 不要

不要分配给你永远不会使用的变量,因为你正在为time_passed这样做。

这样的代码: 如果event.type == QUIT: exit_game() 是罚款,只要你在测试一个或很少的可能性(与if/elif),但不“扩展”无论是可读性还是效率。当你需要支付一些情况下,使用您可以设置循环之前的字典:

dispatch = {pygl.QUIT: exit_game, # whatever else 
      } 

,取而代之的if/elif/else,用途:

f = dispatch.get(event.type) 
if f is None: # the "else" case" 
    ... 
else: f() 
+3

>“我建议避免... import *:”。 'pygame.locals'正是为这种用法而存在的。它包含许多常用的常量,主要是键码和事件类型。 – SingleNegationElimination 2009-09-12 03:28:06

+0

标签/空间4/8混合是一个意外。我使用制表符,而不是空格,因为在jEdit中有空格,我必须退格4次才能进入缩进级别,而且只能使用制表符。不过,我可以随时将它们全部转换为空格。 – mk12 2009-09-12 04:19:40

+0

而字典里的东西,并不是所有的情况下都只有一个声明是一个方法调用,那么这些如何工作呢?我不确定导入部分,为什么他们在文档中说:“作为一种方便,pygame中的大多数顶级变量都放在名为'pygame.locals'的模块中。这应该是与'from pygame.locals import *'一起使用,除了'import pygame'。“ ?感谢您花时间回答,我会再次审视您的意见。 – mk12 2009-09-12 04:25:45

0

这看起来基本上是我见过的其他每个例子。也许你可能想找到一些用pygame编写的开源游戏。

0

我不知道,如果这是那种你正在寻找的答案,但经过
pygame.draw.aaline(屏幕,LINE_COLOUR,(1,1),(639,399))
你应该把
pygame.display.flip()
这样,玩家实际看到的显示将会在每一帧都会刷新。如果你运行这个代码,那么你将看到的只是一个黑屏,没有行,因为显示从不更新。

+0

谢谢,我忘了。我通常总是这样做。 – mk12 2009-09-12 12:55:56

3

你的例子非常好。 但是,如果你看如何运作 “pygame.event.poll()” 看到这个简单的例子:

event = pygame.event.poll() 
    while "ok": 
     event = pygame.event.wait() 
     cursor = pygame.mouse.get_pos() 
     if event.type == QUIT: raise SystemExit 
      if event.type == MOUSEBUTTONUP and pygame.mouse.get_pressed()[0]: 
       print "up" 
     if event.type == MOUSEBUTTONDOWN and pygame.mouse.get_pressed()[0]: 
       print "down" 
     if event.type == KEYDOWN and event.key == K_SPACE: print "space key" 
     if event.type == KEYDOWN and event.key == K_BACKSPACE: 
       print "backspace key" 

可以使用从pygame的所有事件:

  • pygame.event。得到 - 得到 事件队列从队列中获取事件
  • pygame.event.poll - 从队列中取出一个 事件从队列中取出一个 事件
  • pygame.event.wait - 等待从队列

  • pygame.event.clear([pygame.QUIT, pygame.ACTIVEEVENT,pygame.KEYDOWN, PY单 事件game.KEYUP,pygame.MOUSEMOTION, pygame.JOYBUTTONUP, pygame.USEREVENT])从

Bassicaly您创建此事件的功能和使用它的队列中删除所有 事件。 像这样:

def click_down(): 
    #print "Event queue:", pygame.event.peek() 
    return pygame.event.peek(pygame.MOUSEBUTTONDOWN) 

def is_click(): 
    if not click_down(): 
     return None 

    clicks = pygame.event.get(pygame.MOUSEBUTTONDOWN) 
    pygame.event.get(pygame.MOUSEBUTTONUP) 
    return clicks[0].pos 
def quiting(): 
    return pygame.event.peek(pygame.QUIT) 
def keyboard(): 
    pygame.event.pump() 
    pygame.event.get(pygame.KEYDOWN) 

或阻止一些事件,例如:

pygame.event.set_blocked((pygame.JOYAXISMOTION)) 
0

从实证检验很简单,你似乎有一行:

pygame.quit() 

sys.exit前失踪()

2

pygame.Color()上课很好用:

from pygame import Color 

# example: text is 20% gray. gray100 = (255,255,255) 
text_fg = Color('gray20') 
text_bg = Color('gray80') 

# many names are defined 
Color("red") 

# rgb, rgba 
Color(100, 100, 100) 
Color(100, 100, 100, 20) 

#hex 
Color("fefefe") 
Color("fefefe00")