如何阻止pygame无法控制地在字典中循环



我正在尝试制作我的第一个GUI问答游戏。但出于某种原因,当我运行代码来循环处理问题时,它做得太快了,而且没有等到用户在选择一个选项后再转到下一个问题。

迭代次数应该是可变的,因为用户应该能够选择问题的数量,所以我不能为每个问题生成一个函数,而是试图循环浏览字典并将其显示在屏幕上。但是遇到了更多的问题。程序有没有办法等到用户选择其中一个选项后再进入下一个问题。

import pygame
from pygame.locals import *
from gui import Button, FlagButton
from os import path
from q_gen import generate_question
import sys
pygame.init()
WIDTH, HEIGHT = 1000, 600
win = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("World game")
font_path = path.join("fonts", "PartyConfetti.ttf")
small_font = pygame.font.Font(font_path, 50)
centre = ((win.get_width())//2, (win.get_height())//2)
WHITE =        (255, 255, 255)
BLACK =        (  0,   0,   0)
PASTEL_BLUE =  (189, 242, 255)
button_img = pygame.image.load(path.join("assets", "button.png"))
button_img = pygame.transform.scale(button_img, (300, 100))
arrow = pygame.image.load(path.join("assets", "arrow.png"))
arrow = pygame.transform.scale(arrow, (50, 50))
up = pygame.transform.rotate(arrow, 90)
down = pygame.transform.rotate(arrow, 270)
def game():
questions = generate_question("capital", 5, 1)
pressed = False
running = True
while running:

for q in questions:
win.fill(PASTEL_BLUE)
mouse_pos = pygame.mouse.get_pos()
title = small_font.render(f"{q}. {questions[q][0]}", True, "black")
title_rect = title.get_rect(center=(centre[0], centre[1]-200))
win.blit(title, title_rect)
choice1 = Button(win, button_img, (300, 500), "CHOICE")
choice1.changeColor(mouse_pos)
choice1.update()
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
if event.type == pygame.MOUSEBUTTONDOWN:
if choice1.checkForInput(mouse_pos):
pressed = True
break
pygame.display.update()
if pressed:
continue

pygame.quit()
sys.exit(0)

如果需要,按钮的问题生成器和类如下。

from info import info # Large dictionary containing info of countries
from random import choice, randint
modes = ("capital", "flag", "currency")
def generate_question(mode, q_no, difficulty):
questions = {}
new_mode = mode
for i in range(1, q_no+1):
reverse = choice((True, False))
country = choice(list(info.keys()))
choices = []
if mode == "mixed":
new_mode = choice(modes)
if new_mode != "flag":
query = info[country][new_mode]
if reverse:
question = f"Which country is {query} the {new_mode} of?"
answer = country
while len(choices)<=(difficulty-1)*2:
rand_choice = choice(list(info.keys()))
if rand_choice != answer and rand_choice not in choices:
choices.append(rand_choice)
else:
question = f"What is the {new_mode} of {country}?"
answer = query
while len(choices)<=(difficulty-1)*2:
rand_country = choice(list(info.keys()))
rand_choice = info[rand_country][new_mode]
if rand_choice != answer and rand_choice not in choices:
choices.append(rand_choice)
choices.insert(randint(0, len(choices)), answer)
questions[i] = (question, country, new_mode, answer, choices)
else:
question = f"Which one is the flag of {country}?"
answer = f"{country}.png"
return questions
import os
import pygame
pygame.init()
class Button():
def __init__(self, screen, image, pos, text_input, font=os.path.join("fonts", "PartyConfetti.ttf"), text_size=50):
self.screen = screen
self.image = image
self.x_pos = pos[0]
self.y_pos = pos[1]
self.font = pygame.font.Font(font, text_size)
self.rect = self.image.get_rect(center=(self.x_pos, self.y_pos))
self.text_input = text_input
self.text = self.font.render(self.text_input, True, "black")
self.text_rect = self.text.get_rect(center=(self.x_pos, self.y_pos))
def update(self):
self.screen.blit(self.image, self.rect)
self.screen.blit(self.text, self.text_rect)
def checkForInput(self, position):
if position[0] in range(self.rect.left, self.rect.right) and position[1] in range(self.rect.top, self.rect.bottom):
return True
return False
def changeColor(self, position):
if position[0] in range(self.rect.left, self.rect.right) and position[1] in range(self.rect.top, self.rect.bottom):
self.text = self.font.render(self.text_input, True, "white")
else:
self.text = self.font.render(self.text_input, True, "black")
class FlagButton(Button):
def __init__(self, screen, image, pos, text_input, flag_image, font=os.path.join("fonts", "PartyConfetti.ttf"), text_size=50):
super().__init__(screen, image, pos, text_input, font, text_size)
self.flag_image = flag_image
self.flag_image_rect = self.flag_image.get_rect(center=(self.x_pos, self.y_pos))
def update(self):
self.screen.blit(self.image, self.rect)
self.screen.blit(self.flag_image, self.flag_image_rect)

问题在这里

if pressed:
continue

continue不会执行您认为它会执行的操作,它只是跳过当前迭代的其余部分并继续循环。

相反,您可以使用while循环在点击检查上保持循环,直到按下按钮。

import pygame
from pygame.locals import *
from gui import Button, FlagButton
from os import path
from q_gen import generate_question
import sys
pygame.init()
WIDTH, HEIGHT = 1000, 600
win = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("World game")
font_path = path.join("fonts", "PartyConfetti.ttf")
small_font = pygame.font.Font(font_path, 50)
centre = ((win.get_width())//2, (win.get_height())//2)
WHITE =        (255, 255, 255)
BLACK =        (  0,   0,   0)
PASTEL_BLUE =  (189, 242, 255)
button_img = pygame.image.load(path.join("assets", "button.png"))
button_img = pygame.transform.scale(button_img, (300, 100))
arrow = pygame.image.load(path.join("assets", "arrow.png"))
arrow = pygame.transform.scale(arrow, (50, 50))
up = pygame.transform.rotate(arrow, 90)
down = pygame.transform.rotate(arrow, 270)
def game():
questions = generate_question("capital", 5, 1)
pressed = False
running = True
while running:
for q in questions:
win.fill(PASTEL_BLUE)
title = small_font.render(f"{q}. {questions[q][0]}", True, "black")
title_rect = title.get_rect(center=(centre[0], centre[1]-200))
win.blit(title, title_rect)
choice1 = Button(win, button_img, (300, 500), "CHOICE")
while not pressed and running:
mouse_pos = pygame.mouse.get_pos()
choice1.changeColor(mouse_pos)
choice1.update()
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
if event.type == pygame.MOUSEBUTTONDOWN:
if choice1.checkForInput(mouse_pos):
pressed = True
pygame.display.update()
if not running:
break

pygame.quit()
sys.exit(0)

这个代码可能还有一些问题,但希望这能帮助解决你的问题。

最新更新