文本不在循环内更新(在功能内)

时间:2019-12-25 23:27:11

标签: python pygame

我正在尝试使用Python制作自己的OLDTV版本,但是遇到了问题。我要使文本变大一会,然后再调整为常规大小。我遇到的问题是根本不显示文本。如果有帮助,我将使用随附的Spyder编辑器运行Anaconda 2.7(安装在以前的项目中)。

代码:

import pygame
from pygame.transform import scale
from random import randint

def make_font(fonts, size):
    available = pygame.font.get_fonts()
    # get_fonts() returns a list of lowercase spaceless font names
    choices = map(lambda x:x.lower().replace(' ', ''), fonts)
    for choice in choices:
        if choice in available:
            return pygame.font.SysFont(choice, size)
    return pygame.font.Font(None, size)

_cached_fonts = {}
def get_font(font_preferences, size):
    global _cached_fonts
    key = str(font_preferences) + '|' + str(size)
    font = _cached_fonts.get(key, None)
    if font == None:
        font = make_font(font_preferences, size)
        _cached_fonts[key] = font
    return font

_cached_text = {}
def create_text(text, fonts, size, color):
    global _cached_text
    key = '|'.join(map(str, (fonts, size, color, text)))
    image = _cached_text.get(key, None)
    if image == None:
        font = get_font(fonts, size)
        image = font.render(text, True, color)
        _cached_text[key] = image
    return image

pygame.init()
screen = pygame.display.set_mode((640, 480))
real = 0
guess = 0
score = 0
i = 0
gameRunning = False
runEnd = False
clock = pygame.time.Clock()
done = False

font_preferences = [
        "Arial",
        "Times New Roman",
        "Papyrus",
        "Comic Sans MS"]

def endRun(score):
    global gameRunning
    global runEnd
    global i
    screen.fill([255, 255, 255])
    text = create_text(str(score), font_preferences, 72, (0, 0, 0))
    screen.blit(text,
        (320 - text.get_width() // 2, 240 - text.get_height() // 2))
    gameRunning = False
    runEnd = True
    i = 0


def genNext():
    screen.fill([255, 255, 255])
    global real
    gen = randint(1, 2)
    if gen == 2:
        ref = 0
    else:
        ref = 1
    rand1 = randint(1, 6)
    rand2 = randint(1, 6)
    words = ["Red", "Orange", "Yellow", "Green", "Blue", "Purple"]
    if ref == 1:
        if rand1 == rand2:
            real = 0
        else:
            real = 1
        displayWord = words[rand1-1]
        displayCol = rand2
    elif ref == 0:
        real = 0
        displayWord = words[rand1-1]
        displayCol = rand1
    return ReturnValue(displayWord, displayCol)

def displayWordCol(word, col):
    colVal = [(255, 0, 0), (255, 128, 0), (190, 190, 0), (0, 255, 0), (0, 0, 255), (128, 0, 255)]
    for i in range(10, 5):
        text = create_text(word, font_preferences, 72, colVal[col-1])
        scale(text, (text.get_width() * i/5, text.get_height() * i/5))
        screen.blit(text, (320 - text.get_width() // 2, 240 - text.get_height() // 2))
        pygame.display.update()
        clock.tick(60)


def checkNext(real, guess):
    global score
    if real == guess:
        score = score + 1
        e = genNext()
        displayWordCol(e.y0, e.y1)
    else:
        endRun(score)

def homeScreen():
    screen.fill(0)
    text = create_text("OpenTV", font_preferences, 72, (100, 100, 100))
    screen.blit(text,
        (320 - text.get_width() // 2, 240 - text.get_height() // 2))

class ReturnValue:
  def __init__(self, y0, y1):
     self.y0 = y0
     self.y1 = y1

homeScreen()


while not done:
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            done = True
        if event.type == pygame.MOUSEBUTTONDOWN:
                if event.button == 1:
                    if gameRunning == True:
                        guess = 0
                        checkNext(real, guess)
                elif event.button == 3:
                    if gameRunning == True:
                        guess = 1
                        checkNext(real, guess)
        if event.type == pygame.KEYDOWN:
                if event.key == pygame.K_RETURN:
                    if gameRunning == False:
                        gameRunning = True
                        score = 0
                        e = genNext()
                        displayWordCol(e.y0, e.y1)
                if event.key == pygame.K_ESCAPE:
                    if gameRunning == True:
                        endRun(score)
                    elif gameRunning == False:
                        done = True


    if runEnd:
        i = i + 1
        if i == 120:
            homeScreen()
            runEnd = False

    pygame.display.flip()
    clock.tick(60)

引起麻烦的部分是displayWordCol函数。我的代码有问题吗?还是应该切换到IDLE并粘贴我的代码?

1 个答案:

答案 0 :(得分:1)

我认为主要问题是使用scale()缩放呈现的文本。据我所知,scale()用于图像。

仅以此为例(以后可以根据需要进行调整)。

def displayWordCol(word, col):
colVal = [(255, 0, 0), (255, 128, 0), (190, 190, 0), (0, 255, 0), (0, 0, 255), (128, 0, 255)]
    for i in range(10):
        text = create_text(word, font_preferences, int(72 *i/5), colVal[col-1])
        #scale(text, (text.get_width() * i/5, text.get_height() * i/5))
        screen.blit(text, (320 - text.get_width() // 2, 240 - text.get_height() // 2))
        pygame.display.update()
        clock.tick(60)

另一个可能的问题是,您可能需要在每个循环周期中使单词变亮之前先擦除屏幕(不确定要寻找的效果)。

最后,使用pygame几乎总是使用“脏污”矩形的好习惯,仅擦除和更新屏幕上实际已更改的部分。

致谢!

编辑:也尝试此操作。我添加了删除屏幕前的提示。我想这种效果就是您想要的。我还添加了“脏” rects管理作为示例。

def displayWordCol(word, col):
    colVal = [(255, 0, 0), (255, 128, 0), (190, 190, 0), (0, 255, 0), (0, 0, 255), (128, 0, 255)]
    regular_size = 72
    cicles = 20
    size_gap = 5

    initial_size = regular_size + cicles * size_gap
    text = create_text(word, font_preferences, int(initial_size), colVal[col - 1])
    pos = (320, 240)
    rect = pygame.Rect(pos[0] - text.get_width()/2, pos[1] - text.get_height()/2, text.get_width(), text.get_height())

    screen.fill(pygame.Color("white"))
    pygame.display.update()
    for i in range(cicles):
        text = create_text(word, font_preferences, int(initial_size - i*size_gap), colVal[col-1])
        screen.fill(pygame.Color("white"), rect)
        screen.blit(text, (pos[0] - text.get_width()/2, pos[1] - text.get_height()/2))
        pygame.display.update(rect)
        clock.tick(60))