Я сделал эту небольшую игру, которая проверяет наши языковые навыки. Он использует один внешний модуль, pinyin
, который можно установить с помощью команды командной строки
pip install pinyin
Вот как это происходит:
Как вы можете видеть из GIF, игра начинается со случайного выбора символов для верхних ящиков и произношения каждого соответствующего символа для нижних ячеек, разумеется, в случайном порядке.
Каждый раз, когда пользователь вводит символ с правильным произношением, оценка увеличивается на 10, а соответствующие поля отключаются. Каждый раз, когда пользователь вводит символ с неправильным произношением, оценка уменьшается на 5.
Когда все ящики отключены, игра перезагружается с другой случайной выборкой символов, и счет остается на том же значении, что и до отключения всех ящиков.
Вот мой код:
import pygame
from random import sample, shuffle, choice
import pinyin
pygame.init()
pygame.font.init()
wn = pygame.display.set_mode((600, 400))
words="的是不我一有大在人了中到資要可以這個你會好為上來就學交也用能如文時沒說他看提那問生過下請天們所多麼小想得之還"
class Text:
def __init__(self, text, borders, font):
self.font = font
self.color = (255, 255, 0)
self.text = self.font.render(text, True, self.color)
width = self.text.get_width()
height = self.text.get_height()
x, y, w, h = borders
self.pos = x + (w - width) / 2, y + (h - height) / 2
def draw(self):
wn.blit(self.text, self.pos)
class Score:
def __init__(self, pos, font=pygame.font.SysFont("Californian FB", 40)):
self.pos = pos
self.font = font
self.value = 0
self.color = (255, 255, 255)
self.up = 10
self.down = 5
self.potential = 0
def score_up(self):
self.value += 10
def score_down(self):
self.value -= 5
self.potential += 10
def draw(self):
wn.blit(self.font.render(str(self.value), True, self.color), self.pos)
class Box:
def __init__(self, bottom, x, y, w, h, word, font=pygame.font.SysFont("microsoftyaheimicrosoftyaheiui", 23)):
self.rect = pygame.Rect(x, y, w, h)
self.inner_rect = pygame.Rect(x + w * .125, y + h * .125, w * .75, h * .75)
self.box_color = (100, 0, 0)
self.port_color = (50, 0, 0)
self.active_color = (20, 0, 0)
self.disabled = False
self.port = pygame.Rect(x + w / 4, y + h, w / 2, h // 8)
self.word = word
if bottom:
self.port.y -= h + h // 8
word = pinyin.get(word)
self.text = Text(word, (x, y, w, h), font)
def over(self, x, y):
return self.rect.collidepoint(x, y)
def disable(self):
self.disabled = True
self.box_color = (255, 50, 50)
def draw(self, active):
if active:
pygame.draw.rect(wn, self.active_color, self.rect)
pygame.draw.rect(wn, self.box_color, self.inner_rect)
else:
pygame.draw.rect(wn, self.box_color, self.rect)
self.text.draw()
if self.disabled:
return
pygame.draw.rect(wn, self.port_color, self.port)
class Game:
def __init__(self, words, x, y):
self.w = 70
self.h = 50
self.box_x_pad = 30
self.box_y_pad = 120
self.words = words
self.in_boxes = list()
self.out_boxes = list()
self.active_in_box = None
self.active_out_box = None
for i, word in enumerate(words):
in_box = Box(False, x + i * (self.w + self.box_x_pad), y, self.w, self.h, word)
self.in_boxes.append(in_box)
shuffle(words)
for i, word in enumerate(words):
out_box = Box(True, x + i * (self.w + self.box_x_pad), y + self.box_y_pad, self.w, self.h, word)
self.out_boxes.append(out_box)
def won(self):
return all(in_box.disabled for in_box in self.in_boxes)
def draw_lines(self, event):
if self.active_in_box:
if self.active_out_box:
pygame.draw.line(wn, (255, 255, 0), self.active_in_box.port.center, self.active_out_box.port.center, 7)
else:
pygame.draw.line(wn, (255, 255, 0), self.active_in_box.port.center, event.pos, 7)
def draw_boxes(self):
for in_box in self.in_boxes:
in_box.draw(in_box == self.active_in_box)
for out_box in self.out_boxes:
out_box.draw(out_box == self.active_out_box)
bg_color = (200, 0, 0)
game = Game(sample(words, 5), 60, 120)
score = Score((60, 50))
running = True
while running:
wn.fill(bg_color)
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
elif event.type == pygame.MOUSEBUTTONDOWN:
for in_box in game.in_boxes:
if in_box.over(*event.pos) and not in_box.disabled:
game.active_in_box = in_box
break
elif event.type == pygame.MOUSEMOTION:
if game.active_in_box:
for out_box in game.out_boxes:
if out_box.over(*event.pos) and not out_box.disabled:
game.active_out_box = out_box
break
else:
game.active_out_box = None
elif event.type == pygame.MOUSEBUTTONUP:
if game.active_in_box and game.active_out_box:
if game.active_out_box.word == game.active_in_box.word:
game.active_out_box.disable()
game.active_in_box.disable()
score.score_up()
if game.won():
game = Game(sample(words, 5), 60, 120)
else:
score.score_down()
game.active_out_box = game.active_in_box = None
game.draw_lines(event)
game.draw_boxes()
score.draw()
pygame.display.update()
pygame.quit()
Я хочу повысить эффективность своего кода и улучшить концепцию DRY моего кода.