Pyglet 进入 Class

Pyglet Into Class

鉴于到目前为止我一直使用 Pygame,我想开始使用 Pyglet,以了解它的工作原理。

import pyglet, os

class runGame():
    widthDisplay = 1024
    heightDiplay = 576
    title = "Pokémon Life and Death: Esploratori del proprio Destino"

    wra = pyglet.image.load("wra.png")
    wrb = pyglet.image.load("wrb.png")

    def __init__(self):
        platform = pyglet.window.get_platform()
        display = platform.get_default_display()
        screen = display.get_default_screen()
        self.widthScreen = screen.width
        self.heightScreen = screen.height
        self.xDisplay = int(self.widthScreen / 2 - self.widthDisplay / 2)
        self.yDisplay = int(self.heightScreen / 2 - self.heightDiplay / 2)
        self.Display = pyglet.window.Window(width=self.widthDisplay, height=self.heightDiplay, caption=self.title, resizable=False)
        self.Display.set_location(self.xDisplay, self.yDisplay)
        pyglet.app.run()

game = runGame()

到目前为止,一切都很好,一切正常。但是我错了,从某种意义上说,既然我要画东西,我该怎么办?从某种意义上说,Pyglet 是否可以像 Pygame 一样留在 class 中?

你应该为你正在做的每件事做更多的功能。例如,如果你想制作一条线,你可能有

import pyglet, os

class runGame():
    widthDisplay = 1024
    heightDiplay = 576
    title = "Pokémon Life and Death: Esploratori del proprio Destino"

    wra = pyglet.image.load("wra.png")
    wrb = pyglet.image.load("wrb.png")

    def __init__(self):
        platform = pyglet.window.get_platform()
        display = platform.get_default_display()
        screen = display.get_default_screen()
        self.widthScreen = screen.width
        self.heightScreen = screen.height
        self.xDisplay = int(self.widthScreen / 2 - self.widthDisplay / 2)
        self.yDisplay = int(self.heightScreen / 2 - self.heightDiplay / 2)
        self.Display = pyglet.window.Window(width=self.widthDisplay,    height=self.heightDiplay, caption=self.title, resizable=False)
        self.Display.set_location(self.xDisplay, self.yDisplay)
        pyglet.app.run()

    def drawLine(x, y):
        drawLine(x, y)

您必须根据自己的需要创建函数,但是如果您不打算在终止程序之前多次使用 runGame class,则应该不要用OOP编程,用Procedural Programming.

标记的解决方案可能会解决问题。
但是,在我看来,它并没有真正添加比您已经实现的功能更多的功能。

如果你真的想把 Pyglet 变成 class,你实际上必须继承一些东西,或者利用我认为的 OOP 方式编程的可能性。

这是我的两分钱:

import pyglet
from pyglet.gl import *
from collections import OrderedDict
from time import time

key = pyglet.window.key

class main(pyglet.window.Window):
    def __init__ (self, width=1024, height=576, caption="Pokémon Life and Death: Esploratori del proprio Destino", fps=True, *args, **kwargs):
        super(main, self).__init__(width, height, *args, **kwargs)

        platform = pyglet.window.get_platform()
        display = platform.get_default_display()
        screen = display.get_default_screen()

        self.xDisplay = int(screen.width / 2 - self.width / 2)
        self.yDisplay = int(screen.height / 2 - self.height / 2)
        self.set_location(self.xDisplay, self.yDisplay)

        self.sprites = OrderedDict()

        if fps:
            self.sprites['fps_label'] = pyglet.text.Label('0 fps', x=10, y=10)
            self.last_update = time()
            self.fps_count = 0

        self.keys = OrderedDict()

        self.mouse_x = 0
        self.mouse_y = 0

        self.alive = 1

    def on_draw(self):
        self.render()

    def on_close(self):
        self.alive = 0

    def on_mouse_motion(self, x, y, dx, dy):
        self.mouse_x = x
        self.mouse_y = y

    def on_mouse_release(self, x, y, button, modifiers):
        print('Released mouse at {}x{}'.format(x, y))


    def on_mouse_press(self, x, y, button, modifiers):
        if button == 1:
            print('Pressed mouse at {}x{}'.format(x, y))


    def on_mouse_drag(self, x, y, dx, dy, button, modifiers):
        self.drag = True
        print('Dragging mouse at {}x{}'.format(x, y))

    def on_key_release(self, symbol, modifiers):
        try:
            del self.keys[symbol]
        except:
            pass

    def on_key_press(self, symbol, modifiers):
        if symbol == key.ESCAPE: # [ESC]
            self.alive = 0

        self.keys[symbol] = True

    def pre_render(self):
        pass

    def render(self):
        self.clear()

        # FPS stuff (if you want to)
        self.fps_count += 1
        if time() - self.last_update > 1: # 1 sec passed
            self.sprites['fps_label'].text = str(self.fps_count)
            self.fps_count = 0
            self.last_update = time()

        #self.bg.draw()
        self.pre_render()

        for sprite in self.sprites:
            self.sprites[sprite].draw()

        self.flip()

    def run(self):
        while self.alive == 1:
            self.render()

            # -----------> This is key <----------
            # This is what replaces pyglet.app.run()
            # but is required for the GUI to not freeze
            #
            event = self.dispatch_events()

if __name__ == '__main__':
    x = main()
    x.run()

通过这种方式,您实际上可以与您的 class 互动,就像它是 pyglet class 一样。例如,您得到了 on_key_press 而无需使用装饰器等

您可以通过继承 pyglet.window.Window class 创建自定义 pyglet window。之后在你的init方法中调用super classes init(这将调用pyglet.window.Window class中的init)然后覆盖继承的方法(on_draw,on_key_press、on_key_release 等)。之后创建一个更新方法,pyglet.clock.schedule_interval 将在 second.Lastly 中调用 60 次,只需调用 pyglet.app.run() 方法即可。

import pyglet


class GameWindow(pyglet.window.Window):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)

    def on_draw(self):
        self.clear()

    def on_mouse_press(self, x, y, button, modifiers):
        pass

    def on_mouse_release(self, x, y, button, modifiers):
        pass

    def on_mouse_motion(self, x, y, dx, dy):
        pass

    def update(self, dt):
        pass

if __name__ == "__main__":
    window = GameWindow(1280, 720, "My Window", resizable=False)
    pyglet.clock.schedule_interval(window.update, 1/60.0)
    pyglet.app.run()