pygame.error: Текст имеет нулевую ширину;какой лучший способ заставить это работать? - PullRequest
1 голос
/ 01 апреля 2019

Я пытаюсь написать полностью текстовое приключение на основе графического интерфейса пользователя (есть поля, в которых отображается текст, а также кнопки, по которым можно нажимать для перемещения и атаки).У меня возникли небольшие проблемы с отображением ящиков. Ниже приведены строки кода с ошибками:

Соответствующая переменная из импорта в следующем файле:

textWhite = (240, 234, 214)

Где происходит ошибка

from globalvars import *
import pygame

class AbstractBanner:
    def __init__(self, centerX, centerY, width, height, color):
        self.leftX = centerX - width//2
        self.topY = centerY - height//2
        self.width = width
        self.height = height
        self.color = color
        self.gameDisplay = pygame.display.set_mode((scrW, scrH))

class Banner(AbstractBanner):
    def __init__(self, centerX, centerY, width, height, color, text, textSize):
        super().__init__(centerX, centerY, width, height, color)
        self.text = text
        self.textObject = pygame.font.SysFont("arial.ttf", textSize)
    def display(self):
        surface = self.textObject.render(self.text, True, textWhite)
        rect = surface.get_rect()
        rect.center = (self.leftX, self.topY)
        self.gameDisplay.blit(surface, rect)
        pygame.draw.rect(self.gameDisplay, self.color, (self.leftX, self.topY, self.width, self.height))

Усеченная версия, где выполняется вышеуказанный код (без игрового цикла):

class screenDisplay():
    def __init__(self):
        self.state = "TITLE_SCREEN"
        self.states = ["TITLE_SCREEN", "MAIN_GAME", "COMBAT", "CUTSCENE"]
        if self.state == self.states[0]:
            self.showTitleScreen()
def showTitleScreen(self):
        #Background
        background = Banner(scrW//2, scrH//2, scrW, scrH, avocado, "  ", 2)
        background.display()

И здесь, в четвертом .py файле, находится игровой цикл, который выполняетсявыше:

import pygame
import time
from screenDisplay import screenDisplay
import globalvars

# pylint: disable=no-member 
pygame.init() 
# pylint: enable=no-member
clock = pygame.time.Clock()
showGame = screenDisplay()

while not globalvars.gameIsDone:
    for event in pygame.event.get():
        # pylint: disable=no-member 
        if event.type == pygame.QUIT:
            done = True
            pygame.quit() 
            # pylint: enable=no-member
    pygame.display.update()
    clock.tick(30)

Я прочитал этот вопрос о SO, но я не знаю, куда мне поставить строку del или даже то, что я должен удалить.Если решение состоит в том, чтобы поместить эти две строки в один и тот же файл, есть ли альтернативы?

РЕДАКТИРОВАТЬ: О, и самое главное, вот ошибка!

Traceback (most recent call last):
  File "c:\Users\Robertson\Desktop\Personal Projects\pytextrpg\gameLauncher.py", line 9, in <module>
    showGame = screenDisplay()
  File "c:\Users\Robertson\Desktop\Personal Projects\pytextrpg\screenDisplay.py", line 9, in __init__
    self.showTitleScreen()
  File "c:\Users\Robertson\Desktop\Personal Projects\pytextrpg\screenDisplay.py", line 26, in showTitleScreen
    background.display()
  File "c:\Users\Robertson\Desktop\Personal Projects\pytextrpg\Banner.py", line 19, in display
    surface = self.textObject.render(self.text, True, textWhite)
pygame.error: Text has zero width

Ответы [ 2 ]

0 голосов
/ 01 апреля 2019

pygame.quit() не выходит из программы - он только выходит / закрывается pygame - это означает, что он удаляет элементы pygame из памяти.

Но после закрытия pygame он все равно выполняет pygame.display.update(), что создает проблему.

Таким образом, вам потребуется exit() или sys.exit() после pygame.quit() для немедленного выхода из программы.

 if event.type == pygame.QUIT:
     pygame.quit() 
     exit() 
     #sys.exit()

Или вы должны выйти из цикла while, используя скорее globalvars.gameIsDone = Trueвместо done = True и затем используйте pygame.quit() - аналогично ответу @ 9000.

while not globalvars.gameIsDone:
    for event in pygame.event.get():
        # pylint: disable=no-member 
        if event.type == pygame.QUIT:
            globalvars.gameIsDone = True

            # pylint: enable=no-member
    pygame.display.update()
    clock.tick(30)

pygame.quit() 
0 голосов
/ 01 апреля 2019

Не делайте pygame.quit() в цикле событий. Обратите внимание, как вы делаете display.update сразу после него. Выйти как последняя вещь после вы вышли из цикла.

pygame.init()

done = False
while not done and ...:
  for event in pygame.event.get():
    if event.type == pygame.QUIT:
      done = True
      break # Other events became irrelevant.
  pygame.display.update()
  clock.tick(30)

# Now that we're done:
pygame.quit()
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...